G++ 4.9 上静态 constexpr 的未定义引用,没有优化
undefined reference for static constexpr on g++ 4.9 with no optimisation
我有以下代码:
#include<chrono>
#include<iostream>
using namespace std::chrono_literals;
#define MSG "hello"
#define DUR 1000ms
class mwe{
public:
static constexpr auto msg = MSG;
static constexpr auto dur_1 = DUR;
static constexpr std::chrono::milliseconds dur_2 = DUR;
static const std::chrono::milliseconds dur_3;
static constexpr decltype(DUR) dur_4 = DUR;
};
constexpr std::chrono::milliseconds mwe::dur_2;
const std::chrono::milliseconds mwe::dur_3 = DUR;
constexpr decltype(DUR) mwe::dur_4;
int main(void) {
std::cout << "str: " << mwe::msg << std::endl;
std::cout << "dur_1: " << mwe::dur_1.count() << std::endl;
std::cout << "dur_2: " << mwe::dur_2.count() << std::endl;
std::cout << "dur_3: " << mwe::dur_3.count() << std::endl;
std::cout << "dur_4: " << mwe::dur_4.count() << std::endl;
}
如果我编译它(g++ 4.9),通过
g++ -std=c++14 -O2 test.cpp
一切都按预期工作,但是如果我通过以下方式编译它
g++ -std=c++14 -O0 test.cpp
我收到以下错误:
undefined reference to `mwe::dur_1'
我个人喜欢这种方式,dur_1被定义和声明最多,但是如果没有启用优化,它不适用于我的版本中的 g++。因为我知道的所有其他方法(dur_2、dur_3、dur_4)都有其缺点(值冗余,没有自动类型扣除,例如,如果我将 1000ms 更改为 1s,aso。
你知道吗,如果这是一个 gcc 错误,编译可以在生产模式下工作,但没有优化就无法工作?
有没有更可能的方法可以让它工作,而无需定义课外dur_x的位置?
这不是编译器中的错误。
你使用dur1
但从未定义过它。而且,constexpr
和内联初始化器都没有将该声明作为定义。
[C++11, C++14: 9.4.2/3]:
如果非易失性常量static
数据成员是整型或枚举类型,则其在类定义中的声明可以指定大括号或等于初始值设定项,其中作为赋值表达式的每个初始值设定项子句都是常量表达式 (5.19)。文本类型的static
数据成员可以在类定义中使用constexpr
说明符声明;如果是这样,则其声明应指定一个大括号或等于初始值设定项,其中作为赋值表达式的每个初始值设定项子句都是常量表达式。[ 注意:在这两种情况下,成员都可能出现在常量表达式中。如果在程序中使用 (3.2) 的成员,则仍应在命名空间作用域中定义该成员,并且命名空间作用域定义不应包含初始值设定项。
与往常一样,优化级别可能会影响编译器能够和/或愿意报告此类错误的程度。
您可以编写以下内容来定义您的成员:
#include<chrono>
using namespace std::chrono_literals;
#define DUR 1000ms
struct T
{
static constexpr auto dur_1 = DUR;
};
constexpr decltype(T::dur_1) T::dur_1;
相关文章:
- 现代编译器会优化只引用对象子集的局部变量吗
- 当编译时已知引用占用结构中的空间时,是否错过了优化?
- C++14 通过引用返回一个值以优化性能
- 未优化的 constexpr 的未定义引用用作默认参数
- 常量右值引用是否允许对编译器进行额外优化?
- 使用通过引用(通过指针)传递的参数优化 OpenCL 函数中的指针访问
- 编译器是否优化了对常数变量的引用
- c++链接器错误:未定义的引用仅在优化的生成上
- 当函数参数是常量引用临时或按值复制的临时时,为什么 MSVC 优化会破坏 SSE 代码
- 全局指针由优化器解析 - 但引用不是 - 为什么
- 是否允许C++编译器优化未引用的本地对象
- 优化器删除指针取消引用行
- C++强制对变量引用进行编译优化,使之成为直接的
- 一个好的C++编译器会优化一个引用吗
- C++常量引用参数优化
- 为什么C++编译器没有优化未使用的引用变量?
- c++对std::shared_ptr引用的reinterpret_cast进行优化
- 构造函数中的通用引用和返回值优化(rvo)
- 在c++中,如果返回一个指针并立即解引用,这两个操作会被优化掉吗?
- c++编译器会通过“引用”优化掉未使用的返回值吗