C ++ 11编译失败,未定义引用,另一个类内部的显式模板类实例化

时间:2018-09-18 18:59:29

标签: c++11 templates compiler-errors

我尝试通过stackoverflow搜索该示例,但发现的内容无法解决我所看到的问题。

我看到以下编译错误

  

:(。text.startup + 0x7):对`fields :: SECOND'的未定义引用

对于此示例代码段:

#include <iostream>
#include <string>

enum selector
{
    SELECTOR_ONE,
    SELECTOR_TWO,
};

template <selector E>
struct field_t
{
    size_t value;
    constexpr field_t(const size_t i):value(i){}
};

struct fields
{
    static constexpr field_t<selector::SELECTOR_ONE> FIRST{0};
    static constexpr field_t<selector::SELECTOR_TWO> SECOND{1};
};

int main()
{
    std::cout << fields::SECOND.value << std::endl;
    return 0;
}

我实际上可以通过以下修改来进行编译

#include <iostream>
#include <string>

enum selector
{
    SELECTOR_ONE,
    SELECTOR_TWO,
};

template <selector E>
struct field_t
{
    size_t value;
    constexpr field_t(const size_t i):value(i){}
};

template <selector E>
struct fields
{
    static constexpr field_t<E> FIRST{0};
    static constexpr field_t<E> SECOND{1};
};

int main()
{
    std::cout << fields<SELECTOR_TWO>::SECOND.value << std::endl;
    return 0;
}

我有点困惑为什么前者无法编译,因为这实际上是我希望使用默认模板类实例化的原因。由于我使用的是C ++ 11,因此field_t类没有外部链接(在实例化静态constexpr field_t类时),这是使其他field类得以规避的原因。

1 个答案:

答案 0 :(得分:0)

好像我通过在“ fields”结构之外定义字段来克服链接器问题。这很奇怪,因为将数值与静态constexpr一起使用时,我从来没有遇到过这个问题。

#include <iostream>
#include <string>

enum selector
{
    SELECTOR_ONE,
    SELECTOR_TWO,
};

template <selector E>
struct field_t
{
    size_t value;
    constexpr field_t(const size_t i):value(i){}
};

struct fields
{
    static constexpr field_t<selector::SELECTOR_ONE> FIRST{0};
    static constexpr field_t<selector::SELECTOR_TWO> SECOND{1};
};

// This fixes the compile error
constexpr field_t<selector::SELECTOR_ONE> fields::FIRST;
constexpr field_t<selector::SELECTOR_TWO> fields::SECOND;

int main()
{
    std::cout << fields::SECOND.value << std::endl;
    return 0;
}
相关问题