“对class :: function的未定义引用......” - 我链接不正确吗?

时间:2011-03-07 05:20:31

标签: c++ header linker include makefile

我正在研究这个神经网络课程:

class NeuralNet {
public:
    // Public functions
private:
    vectors vect; // Point-of-access for functions in class vectors
    // Private functions
};

我正在使用这个非常简单的makefile:

all: nnet.exe
nnet.exe: main.o neuralnet.o vectors.o
    g++ -o nnet.exe main.o vectors.o neuralnet.o
main.o: main.cpp neuralnet.h
    g++ -ggdb -c main.cpp
vectors.o: vectors.cpp vectors.h
    g++ -ggdb -c vectors.cpp
neuralnet.o: neuralnet.cpp neuralnet.h vectors.h
    g++ -ggdb -c neuralnet.cpp
clean:
    rm -f *.o nnet.exe

当运行g ++来构建最终的可执行文件时,我会遇到以下形式的错误:

neuralnet.o: /path/to/neuralnet.cpp: line# : undefined reference to vectors::fn_name(args)

例如,我定义了一个函数:

template<typename T> void fill_vec(vector<T>&, int, double);

当我调用此函数时,我传递一个为类型vector<double>声明的变量作为第一个参数,链接器报告undefined reference to void vectors::fill_vec<double>(std::vector<double, std::allocator<double> >&, int, double)

class vectors调用NeuralNet实施中对vect的所有功能的调用。但是, neuralnet.cpp neuralnet.h 都包含“vectors.h”的包含,所以我假设我是某种方式链接不正确。

有人看到任何明显的东西吗?

1 个答案:

答案 0 :(得分:2)

除非您在 vectors.h 定义 fn_name(),否则只包括来自 neuralnet.cpp 的标题和 neuralnet.h 是不够的。确保您实际上可以将手指指向该功能体。您可能希望它位于 vectors.cpp

作为模板会改变一切。您应该在头文件中定义模板方法,而不是在.cpp文件中。虽然您可以在源文件中定义fill_vec<T>,但编译器实际上并未为T的任何值实例化,因为在该转换单元中,它不需要任何值实例。你可以为你需要的T的每个值手动实例化它,但是在你声明它的同一个地方的标题中定义函数会更容易。这样,编译器就可以在每个需要的地方使用该定义。您将获得多个实例化(每个实例化一个用于使用它的每个翻译单元),但链接器知道如何合并这些实例。

另见Undefined reference error for template method