constexpr函数可以返回本地对象的指针吗?

cod*_*707 4 c++ c++14

constexpr 函数定义为 (c++14)

constexpr 函数必须满足以下要求:

  • 它不能是虚拟的
  • 它的返回类型必须是 LiteralType 它的每个参数都必须是 LiteralType
  • 至少存在一组参数值,使得函数的调用可以是核心常量表达式的计算子表达式(对于构造函数,在常量初始值设定项中使用就足够了)(C++14 起)。违反此项目符号无需进行诊断。

函数体必须被删除或默认,或者包含除以下之外的任何语句:

  • asm 声明
  • goto 语句
  • 带有除 case 和 default 之外的标签的语句
  • try 块
  • 非文字类型变量的定义
  • 静态或线程存储持续时间的变量的定义
  • 未执行初始化的变量的定义。

现在下面的 func1 满足要求并编译

constexpr int * func1 (int a)
{
  int b = 4;
  return &b;
}
int main()
{
    constexpr int * a = func1(3);
    int arr[*a];  
    std::cout << a << std::endl;
}
Run Code Online (Sandbox Code Playgroud)

现在我的问题是为什么 func1 是 constexpr。它如何在编译时知道局部变量的地址?

我正在使用 gcc 6.4.0

Som*_*ken 5

它如何在编译时知道局部变量的地址?

事实并非如此。

您引用的第三个项目符号永远不会满足:

至少存在一组参数值,使得函数的调用可以是核心常量表达式的计算子表达式(对于构造函数,在常量初始值设定项中使用就足够了)(C++14 起)。违反此项目符号无需进行诊断。

编译器只是不会抱怨它,因为它不需要这样做,直到您尝试在func1需要正确constexpr函数的内部使用它使其抱怨,例如:

std::array<int, func(3)> d;
Run Code Online (Sandbox Code Playgroud)

这不会编译,你的编译器会告诉你原因。

  • @SombreroChicken 在这种情况下,接受与否是一个实施质量问题。在更复杂的情况下,它可能是不可判定的。该标准对于 NDR 来说是正确的 (4认同)