Osu*_*ldo 3 c++ constexpr c++11
我正在尝试使用constexpr编写指向成员函数的链接列表.主要是为了好玩,但它可能有一个有用的应用程序.
struct Foo;
using MethodPtr = void (Foo::*)();
struct Node
{
constexpr Node(MethodPtr method, const Node* next)
: Method(method)
, Next(next)
{}
constexpr Node Push(MethodPtr method)
{
return Node(method, this);
}
MethodPtr Method;
const Node* Next;
};
struct Foo
{
constexpr static Node GetMethods()
{
return Node{&Foo::Method1, nullptr}
.Push(&Foo::Method2)
.Push(&Foo::Method3);
}
void Method1() {}
void Method2() {}
void Method3() {}
};
int main(void)
{
constexpr Node node = Foo::GetMethods();
}
Run Code Online (Sandbox Code Playgroud)
上面的代码在调用GetMethods()时主要给出了以下错误:
const Node{MethodPtr{Foo::Method3, 0}, ((const Node*)(& Node{MethodPtr{Foo::Method2, 0}, ((const Node*)(& Node{MethodPtr{Foo::Method1, 0}, 0u}))}))}' is not a constant expression
Run Code Online (Sandbox Code Playgroud)
有人请解释为什么这不是一个持续的表达?或者是否有一种替代/正确的方法来实现在编译时构建PTMF列表的目标?
编辑:我正在使用avr-gcc 4.9.2的C++编译器.我将在另一个编译器上尝试此代码.
您正在存储非静态存储持续时间临时值的地址,这在常量表达式中是不允许的.此规则的当前版本位于[expr.const]/5(强调我的):
甲常量表达式可以是一个glvalue芯常量表达式,其值指的是一个常量表达式的一个允许的结果的实体(如下面所定义),或一个prvalue芯常量表达式,其值是一个对象,其中,该对象和它的子对象:
引用类型的每个非静态数据成员是指一个实体,它是一个常量表达式的允许结果,和
如果对象或子对象是指针类型,则它包含具有静态存储持续时间的对象的地址,超出此类对象末尾的地址([expr.add]),函数的地址或空指针值.
(C++ 11包含类似的规则(通过地址常量表达式的定义),但是在被C++ 14广义化替换之前,常量表达式规则被多个DR改变了constexpr,我真的不喜欢做标准考古学今天.)
事实上,由于除了返回的每个临时Node创建的内容GetMethods()都Node被销毁;,因此Node返回的内容将包含一个悬空指针.
| 归档时间: |
|
| 查看次数: |
1280 次 |
| 最近记录: |