1

関数をテンプレートに変換したところ、このエラーが発生し始めました。テンプレートの制限を理解していないはずです。なぜこれが壊れているのか誰か教えてもらえますか?

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

Undefined symbols:
  "bool foo<int>(int const&, int const&)", referenced from:
      _main in file1.o
ld: symbol(s) not found

次のコードをリンクすると。コードは単純化されていますが、それでも失敗します。最初のファイルには次が含まれます。

#include <iostream>
template <class T> bool foo (const T&, const T&);

int main ()
{
  int left = 1;
  int right = 2;

  if (foo <int> (left, right))
    std::cout << "foo!" << std::endl;

  return 0;
}

2 番目のファイルには次のものが含まれます。

template <class T> bool foo (const T& left, const T& right)
{
  return true;
}
4

2 に答える 2

3

Uri が示した理由により、テンプレート メソッドは通常、ヘッダー ファイルで定義されます。あなたのものはクラスのメソッドではなく関数であるため、(複数の CPP ファイルによってインクルードされる可能性があるヘッダー ファイルで) 静的またはインラインとして明示的に定義します。

これを foo.h に入れてください

template<class T> inline bool foo (const T& left, const T& right)
{
  return true;
}

これを main.cpp に入れてください

#include <iostream>
#include "foo.h"

int main ()
{
  int left = 1;
  int right = 2;

  if (foo <int> (left, right))
    std::cout << "foo!" << std::endl;

  return 0;
}

cpp コードは、テンプレート関数の宣言全体を認識するようになりました。

その他の解決策は次のとおりです:テンプレート関数でリンカー エラーを回避するにはどうすればよいですか?

于 2009-02-15T02:59:49.367 に答える
2

私が C++ をたくさんやったのは何年も前のことですが、個別のコンパイルの問題に遭遇していると思います。テンプレートは、リンク時ではなく、コンパイル時にインスタンス化されます。

したがって、foo() の呼び出しを行っているときは、新しい関数コードが生成されないという意味で、実際にはテンプレートをインスタンス化していません。リンカーが解決する必要があるシンボルを作成しているだけです。

ただし、2 番目のファイルがコンパイルされると、テンプレートだけが含まれ、インスタンス化されないため、実際に int を処理するバージョンの foo() は生成されません。その結果、すべてをリンクすると、エラーが発生します。

これについて何をすべきかは 100% わかりませんが、その 2 番目のファイルで int を使用して foo() のインスタンス化を強制する必要があると思います (C++ であると仮定)。関数テンプレートではなく、クラステンプレートのみを使用しました。ここの誰かが正確なコードをすぐに提供してくれると確信しています...

于 2009-02-15T02:55:45.133 に答える