2

ARPACKライブラリを で実行しようとしていVS2010ます。

++ が提供する C++ ラッパーを使用したいと思いARPACKます (いくつかの背景 - 巨大な行列の固有値と固有ベクトルを取得する必要があります)。このテーマに関する非常に優れたチュートリアルがここにあります。

g77onを使用して fortran コードをコンパイルすることができたチュートリアルに従って、説明どおりmingwに dll と lib を正常に生成しました。Visual Studio プロジェクトをライブラリにリンクしようとすると、問題が発生します。

リンクしようとしている方法は次のとおりです。

  1. シンプルな VS2010 C++ コンソール アプリを作成しました
  2. ARPACK++ ライブラリを含むフォルダーを「追加のインクルード フォルダー」に追加しました。
  3. libファイルを「追加の依存関係」に追加しました
  4. libファイルを含むディレクトリを「追加のライブラリディレクトリ」に追加しました

この短いテストコードをコンパイルしようとすると、これらの設定にもかかわらず:

#include "stdafx.h"
#include "arrsnsym.h"

int _tmain(int argc, _TCHAR* argv[])
{
    ARrcNonSymStdEig<float> prob(100, 4L);
    printf("Bok!");
    return 0;
}

次のようなエラーが表示されます。

>arpackcpp.obj : error LNK2001: unresolved external symbol scopy_
1>arpackcpp.obj : error LNK2001: unresolved external symbol snaupd_
1>arpackcpp.obj : error LNK2001: unresolved external symbol sneupd_

リンカが言及されたメソッドを見つけられない理由がわかりません。dllwrap ユーティリティによって生成された .def ファイルを調べると、実際にこれらすべての機能が言及されているため、それらが利用可能であると確信しています。それでも、明らかな何かが欠けていると感じています。

更新(機能しました!):

構成設定でx86に切り替え、生成されたdefファイルを構成プロパティ->リンカー->入力->追加定義ファイルに含めると、64ビットプログラムを32ビットライブラリにリンクしようとしていたことがわかりました。 32ビットの場合(ただし、64が必要でした)。私にとってうまくいった最終的な解決策は、LinuxでMinGWとgfortranを使用してWin64用にクロスコンパイルすることでした。これは驚くほどうまく機能し、VS の 64 ビット C++ アプリからリンクできる dll を生成しました。これを行う方法についてのチュートリアルを書く必要があると思います:)

4

1 に答える 1

0

私の推測では、これは名前マングリング スキームの問題です。Fortran では、シンボルがオブジェクト ファイルのシンボル テーブルにどのような名前を持つかは明確に定義されていません。たとえば、 という名前のルーチンは、、、などfooとしてシンボル テーブルに配置される可能性があります。最近では、2 つのアンダースコアを使用するコンパイラが多すぎることを知りません (g77 は例外です)。ARPACK++ ラッパーは単一のアンダースコアを想定していると思います。ここでの解決策は、シンボル名に単一のアンダースコアを使用するようにコンパイラに指示することです ( with 、つまり using を意味します)。ご了承くださいfooFOOfoo_foo__g77-fno-second-underscoregfortranは、デフォルトで単一のアンダースコアリングを行う新しい (まだサポートされている) オープンソースの fortran コンパイラです。そのコンパイラを使用してコードをビルドすることもできます。(g77 よりも最適化された出力が生成される可能性があります。)

于 2012-07-30T15:09:51.990 に答える