【解決方法】C++ でのリンク時の関数への未定義参照


list.h:

C++
class list {
  private:
  int mCount = 5;

  public:
  int getCount();
};

core_list.cpp:

C++
#include "list.h"

int list::getCount() {
  return mCount;
}

main.cpp:

C++
#include "list.h"
#include <iostream>
int main() {
  list newList;
  std::cout << newList.getCount();
  getchar();
  return 0;
}

メイクファイル:

default:
  g++ -c *.cpp -O2 -Wall
  g++ -o Game.exe *.o
  rm -f *.o *~

私に与えます:

main.o:main.cpp:(.text.startup+0x6d): undefined reference to `list::getCount()'
collect2.exe: error: ld returned 1 exit status
Makefile:2: recipe for target 'default' failed
mingw32-make: *** [default] Error 1

しかし、Makefile を変更すると:

<pre lang="text">
default:
  g++ -c *.cpp -O2 -Wall
  #g++ -o Game.exe *.o
  rm -f *.o *~

したがって、コンパイルするだけでリンクはせず、コンパイルします。 リンクしないだけ
理由はともかく。 お手伝いありがとう。

私が試したこと:

.cpp ファイルの名前をそれぞれの .h ファイルと同じ名前に変更しようとしましたが、役に立ちませんでした。 Makefile も変更しましたが、コンパイルはできますが、リンクしないだけであることに気付きました。

解決策 1

実験として、次の実装を行ってください。 list::getCount() それを main.cpp ファイルに入れます。 正しくコンパイルおよびリンクされるはずです。 もしそうなら、それはリンカーがオブジェクトファイルを見ていないことを意味します core_list.cpp.

Makefile でその行をコメントアウトしてもリンクしない理由は、その行がリンクを行うためです。 どちらかといえば、オブジェクト ファイルを削除する次の行をコメント アウトする必要があります。 これにより、生成されたオブジェクトファイルがあるかどうかを確認できます core_list.cpp.

解決策 2

あなたのソースコードとメイクファイルは私の Windows 11 システム (MinGW32-Make 3.82.90、g++ 10.3.0)。

コマンドラインから試してみることをお勧めします:

g++ -c *.cpp -O2 -Wall

その後

g++ -o Game.exe *.o

最後のコマンドラインでリンクエラーが発生した場合は、試してください

g++ -o Game.exe main.o list.o

解決策 3

ディレクトリにある .cpp ファイルを確認します。 ワイルドカードを使用しているときに、予期しないものにリンクしている可能性があります。 さらに良いことに、make の機能を使用します。

作る
CXXFLAGS = -Wall -Wextra -O2

Game.exe: core_list.o main.o
       $(CXX) $^ -o $@

clean:
       rm Game.exe *.o *~

ここで、make.exe が list.o と main.o に依存していること、および特定のルールを追加せずにそれらを作成する方法を知っていることを確認します。 list.cpp を変更すると、make はそのソース ファイルのみをコンパイルし、以前にコンパイルされた main.o を使用してリンクします。これは、大規模なプロジェクトの場合、時間を大幅に節約できます。 さらに良いことに、.o ファイルが list.h に依存していることを make に伝えることができるので、core_list.h を変更した場合は再コンパイルする必要があります。

作る
CXXFLAGS = -Wall -Wextra -O2
core_list.o:  core_list.cpp list.h
main.o: main.cpp list.h

Game.exe: core_list.o main.o
      $(CXX) $^ -o $@

clean:
      rm Game.exe *.o *~

コメント

タイトルとURLをコピーしました