首页
学习
活动
专区
工具
TVP
发布
社区首页 >问答首页 >对静态常量char[] char[]的引用未定义

对静态常量char[] char[]的引用未定义
EN

Stack Overflow用户
提问于 2011-11-05 07:11:45
回答 4查看 64.9K关注 0票数 215

我想在我的类中有一个static const char数组。GCC抱怨说我应该使用constexpr,尽管现在它告诉我这是一个未定义的引用。如果我将数组设为非成员,那么它就会编译。怎么一回事?

代码语言:javascript
复制
// .hpp
struct foo {
  void bar();
  static constexpr char baz[] = "quz";
};

// .cpp
void foo::bar() {
  std::string str(baz); // undefined reference to baz
}
EN

回答 4

Stack Overflow用户

发布于 2017-10-13 06:02:36

这确实是C++11中的一个缺陷--正如其他人所解释的那样,在C++11中,静态常量表达式成员变量不同于任何其他类型的常量表达式全局变量,它具有外部链接,因此必须在某个地方显式定义。

还值得注意的是,在使用优化进行编译时,您经常可以在没有定义的情况下使用静态常量表达式成员变量,因为它们最终可以在所有使用中内联,但是如果您在没有进行优化的情况下进行编译,那么您的程序将无法链接。这使得这成为了一个非常常见的隐藏陷阱--你的程序在优化的情况下编译得很好,但是一旦你关闭了优化(可能是为了调试),它就无法链接。

不过,好消息是-这个缺陷已经在C++17中修复了!不过,这种方法有点复杂:在C++17中,静态常量表达式成员变量are implicitly inline。拥有inline applied to variables是C++17中的一个新概念,但它实际上意味着它们在任何地方都不需要显式定义。

票数 46
EN

Stack Overflow用户

发布于 2016-04-19 22:40:22

更优雅的解决方案是不是将char[]改为:

代码语言:javascript
复制
static constexpr char * baz = "quz";

这样,我们可以在一行代码中定义/声明/初始化式。

票数 6
EN

Stack Overflow用户

发布于 2018-08-30 19:49:46

对于静态成员的外部链接,我的变通方法是使用constexpr引用成员getter(这不会遇到问题@gnzlbg作为对@deddebme的回答的注释提出的)。

这个习惯用法对我来说很重要,因为我不喜欢在我的项目中有多个.cpp文件,并试图将数量限制为一个,其中只包含#include和一个main()函数。

代码语言:javascript
复制
// foo.hpp
struct foo {
  static constexpr auto& baz() { return "quz"; }
};

// some.cpp

  auto sz = sizeof(foo::baz()); // sz == 4

  auto& foo_baz = foo::baz();  // note auto& not auto
  auto sz2 =  sizeof(foo_baz);    // 4
  auto name = typeid(foo_baz).name();  // something like 'char const[4]'
票数 5
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/8016780

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档