在定义失败之前使用constexpr函数

Use of constexpr function before definition fails

本文关键字:constexpr 函数 定义 失败      更新时间:2023-10-16

我在constexpr上遇到了一些问题。C++初级读本显示了一行代码:

  constexpr int sz = size(); // only size() is a constexpr function
                             // this code is right

然而,这本书并没有给出具体的例子。所以我自己尝试以下代码:

#include <iostream>
constexpr int fun();
int main()
{
    constexpr int f = fun();
    std::cout << f << std::endl;
}
constexpr int fun()
{
    return 3;
}

但是我的编译器说fun()是未定义的。

如果我将constexpr更改为const,它工作得很好,如果我在使用之前更改代码以定义constexpr函数:

#include <iostream>
constexpr int fun()
{
    return 3;
}
int main()
{
    constexpr int f = fun();
    std::cout << f << std::endl;
}

它也运行良好。有人能告诉我为什么吗?

constexpr函数在首次使用之前不必定义,但是在定义之前进行的任何调用的结果都不是常量表达式。

来源:C++标准草案n4296,第5.20节:

条件表达式e核心常量表达式,除非e的求值遵循抽象机的规则,将求值以下表达式之一:

  • this,除了在作为e的一部分而被评估的constexpr函数或constexpr构造函数中
  • 对文字类的constexpr构造函数以外的函数的调用、constexpr函数的调用或对平凡析构函数的隐式调用[注意:重载解析应用为普通——尾音]
  • 调用未定义的constexpr函数或未定义的constexpr构造函数

草案3485的版本(第5.19节):

条件表达式核心常量表达式

  • this[注意:在计算常量表达式时,函数调用替换将constexpr成员函数中每次出现的this替换为指向类对象的指针。--结束注释]
  • 对文字类或constexpr函数的constexpr构造函数以外的函数的调用[注意:重载解析照常应用--结束注释]
  • 调用未定义的constexpr函数或未定义的constexpr构造函数

n2235中的示例int x2 = s. t();实际上由于在标准化之前所做的更改而变得有效。但是,constexpr int x2 = s. t();仍然是一个错误。

常量表达式函数必须在首次使用前定义。见本文件第4.1节末尾。