【问题标题】:undefined reference on make_pair with static const带有静态常量的 make_pair 上的未定义引用
【发布时间】:2014-09-29 09:24:56
【问题描述】:

以下代码在我的 class.cpp 中给出了 gcc 4.7 的错误:

  auto TLV1 = std::make_pair(UNSIGNEDCHAR_STATIC_CONST, Value1); 
  auto TLV2 = std::make_pair(UNSIGNEDCHAR_STATIC_CONST, Value2); 

UNSIGNEDCHAR_STATIC_CONST 是在类中定义的static const unsigned char,值是在函数中定义的vector<unsigned char>

编辑:在我的 class.h 中:

static const unsigned char UNSIGNEDCHAR_STATIC_CONST = 0x4F;

链接器错误:

 undefined reference to `foo::UNSIGNEDCHAR_STATIC_CONST'
 undefined reference to `foo::UNSIGNEDCHAR_STATIC_CONST'

以下代码不会重现错误:

  unsigned char t = UNSIGNEDCHAR_STATIC_CONST;
  auto TLV1 = std::make_pair(t, Value1); 
  auto TLV2 = std::make_pair(t, Value2); 

编辑: 多亏了 Neil Krik 通过选角,我使它工作正常:

auto TLV1 = std::make_pair(static_cast(UNSIGNEDCHAR_STATIC_CONST), Value1); 

或 Vlad 解决方案,在 cpp 文件中:

const unsigned char foo::UNSIGNEDCHAR_STATIC_CONST= 0x4F

【问题讨论】:

  • 我不知道,这就是我问的原因......
  • C++ 中存在一个问题,您在类定义中有一个静态 const,并尝试将它与一个需要引用的函数一起使用。这可能会在 C++11 中以某种方式解决,可能使用constexpr,我不知道。试试std::make_pair((unsigned char)(UNSIGNEDCHAR_STATIC_CONST), Value1);
  • UNSIGNEDCHAR_STATIC_CONST 声明的完整代码行是什么?
  • 演员正在工作。 @Niall 我已经用这行编辑了 ...
  • 因为 make_pair 可能需要引用,但是除非您在类之外(可能在源文件中)为静态 const 提供定义,否则它也没有分配内存来获取引用。强制转换只是将值复制到临时局部变量中并传递它。这只是 C++ 的一个怪癖。

标签: c++ gcc c++11


【解决方案1】:

编译器要求定义这个静态成员。目前只在类中声明。

在某些 cpp 模块中包含以下行

const unsigned char foo::UNSIGNEDCHAR_STATIC_CONST;

根据 C++ 标准

3 如果非易失性 const 静态数据成员是整数或 枚举类型,其在类定义中的声明可以指定 一个大括号或相等初始化器,其中每个初始化器子句是 赋值表达式是一个常量表达式 (5.19)。静态数据 文字类型的成员可以在类定义中声明为 constexpr 说明符;如果是这样,其声明应指定一个 大括号或相等初始化器,其中每个初始化器子句是 赋值表达式是一个常量表达式。 [注:在这两个 在这些情况下,成员可能出现在常量表达式中。 ——尾注 ] 该成员仍应在命名空间范围内定义,如果它是 程序中的 odr-used (3.2) 和命名空间范围定义 不应包含初始化程序

【讨论】:

  • 谢谢。它正在工作,所以如果我理解得很好,当我在头文件中定义以下内容时:static const unsigned char UNSIGNEDCHAR_STATIC_CONST = 0x4F;,没有分配内存,我不能使用 is 作为右值?
  • @MoKaT 编译器只有在不需要它的地址时才能使用它。例如,您可以使用此常量来定义数组的大小。编译器只是在编译时用它代替值。类的静态数据成员仅在类中声明。如果它们用于 ODR,则必须对其进行定义(C++ 标准中有这样的术语)。
  • @MoKaT 查看我更新的帖子。有一个错字。如果在类中的声明中指定了静态 const 数据成员的初始化程序,则不应在数据成员的定义中指定它。
  • 好的,非常感谢。我现在将在我的 .cpp 文件中初始化我的静态常量,它正在工作。请注意,获得此功能的另一种方式(我认为丑陋的方式)是将其转换为相同的类型。
  • @MoKaT 通常在类定义中初始化它们很有用,编译器可以在编译时在类定义中使用它们的值。
猜你喜欢
  • 1970-01-01
  • 2011-02-07
  • 1970-01-01
  • 1970-01-01
  • 2016-08-04
  • 1970-01-01
  • 2020-08-04
相关资源
最近更新 更多