用const初始化constexpr:对int和double的不同处理 [英] Initializing constexpr with const: Different treatment for int and double

查看:148
本文介绍了用const初始化constexpr:对int和double的不同处理的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

以下代码无法编译在Ideone上运行

#include <iostream>
using namespace std;

int main() {
    const double kPi = 3.14;
    constexpr double kPi2 = 2.0*kPi;
    cout << kPi2;
}

错误消息是:


prog.cpp: In function 'int main()':
prog.cpp:6:30: error: the value of 'kPi' is not usable in a constant expression
  constexpr double kPi2 = 2.0*kPi;
                              ^
prog.cpp:5:15: note: 'kPi' was not declared 'constexpr'
  const double kPi = 3.14;


替换 const constexpr kPi 的$ c>声明rel = noreferrer>编译成功。

Substituting the const declaration for kPi with constexpr, it compiles successfully.

另一方面,当 int 为使用而不是 double ,似乎是 const 玩的很好 constexpr

On the other hand, when int is used instead of double, seems like const plays well with constexpr:

#include <iostream>
using namespace std;

int main() {
    const int k1 = 10;
    constexpr int k2 = 2*k1;
    cout << k2 << '\n';
    return 0;
}

为什么 int double 对于使用 const 初始化 constexpr 会得到不同的处理方式

这是Ideone编译器中的错误吗? C ++标准要求吗?为什么?

上面的代码是UB吗?

Why do int and double get different treatments for initializing a constexpr with const?
Is this a bug in the Ideone compiler? Is this required by the C++ standard? Why is that?
Was the above code UB?

PS 我尝试使用Visual Studio 2015 C ++编译器,并且它会编译第一个代码片段(用 const 初始化 constexpr )。

P.S. I tried with Visual Studio 2015 C++ compiler, and it compiles the first code snippet (initializing constexpr with const) just fine.

推荐答案

对于要在编译时计算的constexpr,在该constexpr的初始化中使用的所有内容也必须在编译时计算。
如果将某些内容声明为const,则并不意味着该值将在编译时可用。

The for a constexpr to be calculated at compile time everything that is used in the initialization of that constexpr also must be calculatable at compile time. If you declare something as const it does not mean that the value will be available at compile time.

执行以下行:

const double dbl = 2.;

未指定 double 的表示形式按照标准,因此操作系统将不得不处理此问题。因此,当操作系统加载您的程序时,二进制文件中会包含一个特殊的汇编子例程,该子例程将使这种情况发生。
如果使用 int ,则表示是由标准指定的,因此编译器将知道如何使用它。但是,也可以通过将 double 设置为 constexpr 来实现相同的功能,因此编译器将在编译时对其进行计算。在这种情况下, double 还将是 const (您不能创建 constexpr 而不使它成为 const )。

The double's representation is not specified by the standard so the OS will have to deal with this. So when your program is loaded by the OS there is a special assembly subroutine in your binary that will make this happen. If you use an int the representation is specified by the standard so the compiler will know how to work with it. However the same can be achieved by making the double a constexpr as well, so the compiler will compute it in compile time. In this case the double will also be a const (you cannot make something constexpr without also making it const).

因此这将起作用:

constexpr double kPi = 3.14;
constexpr double kPi2 = 2.0*kPi;

如果使用整数,则编译器将在编译时设置该const的值,因此constexpr将

If you use an int the compiler will set the value of that const at compile time so the constexpr will work.

请记住,不同的编译器可以将 const 解释为 constexpr 在某些情况下并使其起作用。但这不是标准的一部分。

Keep in mind that different compilers can interpret const as constexpr in some cases and make it work. But that is not part of the standard.

这篇关于用const初始化constexpr:对int和double的不同处理的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆