1

我知道 ISO C 标准在分离翻译行为和执行行为方面做了很多工作,部分原因是为了确保交叉编译器不必携带每个目标的执行环境。

我的意思是,与正在运行的程序相比,编译器可用的信息有限。这限制了您可以在源代码中执行的操作,例如不根据函数的返回值初始化变量,如下所示:

int twice (int val) { return val * 2; }
int xyzzy = twice (7);
int main () { printf ("%d\n", xyzzy); return 0; }

我很好奇的是 C++11 中用户定义的文字如何适应这个方案。由于文字评估依赖于一个函数,因此阻止该函数执行以下操作:

  • 返回一个随机值(即使基于输入,例如42_roughly给你一个 40 到 44 之间的值)?
  • 有副作用,例如更改全局变量?

必须调用函数这一事实是否意味着在编译时计算的意义上这些并不是真正的文字?

如果是这样的话,这些文字相对于任何其他函数调用的优势是什么。换句话说,为什么是:

int xyzzy = 1101_1110_b;

最好:

int xyzzy = makeBin ("1101_1110");

?

4

1 回答 1

6

秘密在于您是否将用户定义的文字函数声明为constexpr

比较这个(正常的执行时间函数):

#include <iostream>
int operator "" _twice(unsigned long long num) { return num*2; }
int xyzzy = 7_twice;
int main () { std::cout << xyzzy << "\n"; return 0; }

有了这个(编译时常量,static_assert工作):

#include <iostream>
constexpr int operator "" _twice(unsigned long long num) { return num*2; }
int xyzzy = 7_twice;
int main () {
    static_assert(7_twice == 14, "not compile time constant");
    std::cout << xyzzy << "\n";
    return 0;
}

显然,声明一个函数会将其中的constexpr所有语句限制为constexpr也或编译时常量;不允许使用随机数恶作剧。

于 2013-06-21T05:19:35.600 回答