search

Home  >  Q&A  >  body text

c++ - 关于constexpr函数的一个问题

先看代码

#include <iostream>
#include <cstdlib>
#include <cstdio>
//#include "test.h"

using namespace std;

constexpr int screen(int x)
{
   return x; 
}


int main()
{   
    int x = 0;
    int z =  screen(x);
    cout << z<<endl;
    return 0;
}

  在C++ Primer一书中说到constexpr函数定义的约定:函数的返回类型以及所有的形参类型必须是字面值类型(即编译过程就能得到结果的类型)。但是同时又说constexpr函数不一定返回常量表达式。感觉前后有一些矛盾,就像上面的代码一样,通过 g++ test.cpp -std=c00x 的编译运行都是没有问题的,这里应该怎么理解?

天蓬老师天蓬老师2813 days ago625

reply all(3)I'll reply

  • 黄舟

    黄舟2017-04-17 13:33:24

    看看这个:A constexpr function is not required to return a constant expression?

    reply
    0
  • 黄舟

    黄舟2017-04-17 13:33:24

    C++ standard document n45675.20 section talks about this

    int main()
    {   
        int x = 0;
        int z =  screen(x); //因为z是非constexpr的,不要求screen是constexpr的
        cout << z<<endl;
        return 0;
    }
    int main()
    {   
        int x = 0;
        constexpr int z =  screen(x); //错误!! x的lifetime开始于screen(x)的外部
        cout << z<<endl;
        return 0;
    }
    int main()
    {  
        constexpr int z =  screen(0); //screen(0)是常量表达式, 对于screen内部,x的lifetime开始于函数内部
        cout << z<<endl;
        return 0;
    }

    reply
    0
  • PHPz

    PHPz2017-04-17 13:33:24

    You can think of it this way: C++ does not require that the constexpr function must return a constant expression (take the screen constexpr function in the question as an example)

    • If you are in a context that does not require a constant expression, such as: int z = screen(x); You do not need to return a constant expression. At this time, the compiler will not check whether the result of the function will return a constant expression.

    • If it is in a context that requires a constant expression, such as: constexpr int z = screen(x); Then the constexpr function must be able to return a constant expression. At this time, the compiler will check whether the result returned by the function is a constant expression, and if not, an error will be reported.

    reply
    0
  • Cancelreply