在constexpr函数体c ++ 14中可以有非文字类型的定义变量吗?

时间:2014-02-14 19:03:20

标签: c++ c++11 language-lawyer constexpr c++14

我认为在C ++ 14中,从constexpr中删除了更多限制。但根据N3797 7.1.5 3-punct:


contexpr函数shal的定义满足以下约束:

  • 它不应该是虚拟的
  • 其返回类型应为文字类型;
  • 每个参数类型都应为文字类型;
  • function-body 应为= 删除,= 默认,或者复合语句不含:
    • asm-definition
    • 转到声明,
    • a try-block
    • 非文字类型或静态或线程存储持续时间的变量的定义,或者没有初始化的定义 执行。

我知道为什么不允许静态,线程存储持续时间变量,但我没有看到任何理由,为什么只允许定义文字类型的变量?

或者我不明白标准。

我不确定,但是根据标准的跟随错误应该创建,即使是C ++ 14:

struct point{
constexpr point(): x(0), y(0){}
constexpr point(int x_, int y_): x(x_),y(y_){}
constexpr int hypot()const { return x*x + y*y; }
int x,y;
};

constexpr int hypot(int x, int y) {  
   point p{x,y}; //error, because p - is not literal type.
   return p.hypot();
}

// error, because return type is not literal.
constexpr point  getPoint(int x, int y) { return {x,y}; }

// error, because parameter is not literal.
constexpr int hypot(point p) { return p.hypot(); }

问:如果真的发生错误,为什么不删除这些限制?

1 个答案:

答案 0 :(得分:12)

文字类型在3.9 / 10中定义:

  

类型是文字类型,如果它是:

     
      
  • void;或

  •   
  • 标量类型;或

  •   
  • 参考类型;或

  •   
  • 一个文字类型的数组;或

  •   
  • 具有以下所有属性的类类型(第9条):

         
        
    • 它有一个简单的析构函数,

    •   
    • 它是聚合类型(8.5.1)或至少有一个constexpr构造函数或构造函数模板,它不是复制或移动构造函数,并且

    •   
    • 所有非静态数据成员和基类都是非易失性文字类型

    •   
  •   

所以你的struct point 一个文字类型,你的示例代码是有效的C ++ 1y。

至于为什么constexpr函数被限制为文字类型的变量,它们是唯一保证在编译时可解释的类型。