【问题标题】:Why is a function not defined in the .o file for this C++ class?为什么这个 C++ 类的 .o 文件中没有定义函数?
【发布时间】:2010-11-09 13:55:08
【问题描述】:

我有一个正在使用的 C++ 类,当我使用 `nm --demangle' 查看 .o 文件时,其中有一个函数没有显示,而当程序试图运行,即使一切正常。

标题看起来像:

#ifndef __COLLECTION_H
#define __COLLECTION_H

#include <vector>

#include "ObjectInstance.h"

using namespace std;

template <class T>
class Collection : public ObjectInstance
{       
protected:
    vector<T*> items;
    void internalInsertAt(T* item, int index);
    void internalRemoveIndex(int index);
    void internalRemoveItem(T* item);

public:
    virtual ~Collection();
    // Specific functions for this interface
    static int item(jsplugin_obj *this_obj, jsplugin_obj *function_obj, int argc, 
    T* internalGetItem(int index);
    int getSize();
    void addItem(T* item);
};

#endif

addItem函数实现为

template <class T>
void Collection<T>::addItem(T* item)
{   
    items.push_back(item);
}   

我得到的错误是当我尝试在另一个类中继承这个类并在运行时出现:undefined symbol: _ZN10CollectionIN4NJSE5TrackEE7addItemEPS1_

我觉得我在这里遗漏了一些简单的东西,但不知道是什么。

【问题讨论】:

  • 链接的时候你真的指定了库吗?

标签: c++ templates linker


【解决方案1】:

函数在头文件还是源文件中?处理模板最简单的方法是将所有模板定义放在头文件中,以保证该定义对任何实例化它的代码都是可用的。

【讨论】:

    【解决方案2】:

    嗯,我认为这是因为该函数是模板的成员。在 C++ 中,您不能编译模板(至少不容易)。如果要分发模板类,把所有代码都写在header里。

    【讨论】:

      【解决方案3】:

      编译器需要访问addItem 的整个模板定义(不仅仅是签名),以便为模板的每个实例化生成代码,因此您需要将其定义移动到您的标头,即遵循@ 987654321@.

      事实上,现代 C++ 编译器并不容易支持模板的单独编译模型。

      【讨论】:

      【解决方案4】:

      单独编译单元中的模板可能是一场噩梦,需要大量繁重的编译器。

      请记住,必须为您尝试为其实例化模板的每种类型 T 编译模板函数的特定版本。

      因此,最简单的方法是将所有模板函数定义放入“.h”头文件中。

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 2021-11-06
        • 1970-01-01
        • 2013-05-11
        • 2014-04-11
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        相关资源
        最近更新 更多