为什么这个代码在Coliru上编译而在Xcode上编译?

时间:2016-04-26 13:13:51

标签: c++ xcode templates abstract-class crtp

我有时使用前者作为测试平台,然后将代码移动到我在XCode中的真实项目中。在这种情况下,这对我不起作用。以下代码在Coliru上编译并运行(请参阅cat /Archive2/48/70c3935989bffb/main.cpp),但不在XCode上运行。

#include <cassert>

template <typename T, typename P>
class Permutation
{
public:

    virtual bool operator==(const P& other) const;
    // other member functions not listed here use the type T
};

template <typename T>
class SmallPermutation : public Permutation<T, SmallPermutation<T> >
{    
public:

    SmallPermutation(int i);    
    virtual bool operator==(const SmallPermutation& other) const;
    int code;
    // other member functions not listed here use the type T
};


template <typename T>
SmallPermutation<T>::SmallPermutation(int i)
{
    code = i;
}

template <typename T>
bool SmallPermutation<T>::operator==(const SmallPermutation& other)  const
{
    return code == other.code;
}

int main()
{    
    SmallPermutation<int> a(4);
    SmallPermutation<int> b(7);
    SmallPermutation<int> c(4);

    assert(a == c);
    assert(!(a == b));

    return 0;
}

以下是来自XCode的错误消息的一部分(我不明白):

Undefined symbols for architecture x86_64:
"Permutation<int, SmallPermutation<int> >::operator==(SmallPermutation<int> const&) const", referenced from:
  vtable for Permutation<int, SmallPermutation<int> > in permutationTest.o
ld: symbol(s) not found for architecture x86_64
clang: error: linker command failed with exit code 1 (use -v to see invocation)

代码有什么不标准的吗?我需要调整XCode中的构建/编译/环境设置吗?

背景:我有几个(模板)类具有相同的接口,并希望它们都从一个抽象类继承。模板的东西让这个任务变得有点困难。我使用(可能是错误的)一种名为CRTP(奇怪的重复模板模式)的技术来实现它。

1 个答案:

答案 0 :(得分:1)

如果声明一个非纯虚函数,比如operator==类中的Permutation函数,那么它需要有一个定义,你必须为函数提供一个函数体。

解决方案是让它变得纯净:

virtual bool operator==(const P& other) const = 0;

或提供虚拟实现:

virtual bool operator==(const P& other) const { return false; }