与引用一起使用的列表,在用作成员时更改行为
List using with references, changes behavior when used as a member
在试验这个问题/答案 https://stackoverflow.com/a/50649120/225186,我产生了一个似乎是实现循环列表的法律递归自引用类:
struct node{
int val;
node const& next;
};
int main(){
node s{3, {4, s}};
assert(s.val == 3);
assert(s.next.val == 4);
assert(&s.next.next == &s);
assert(s.next.next.val == 3);
}
但是,当我尝试将其作为较大类的成员时,我会收到编译器的警告,并且行为发生了变化。
struct A{
node n;
int i;
A(int a, int b) : n{a, {b, n}}{} // warning here, also tried n{a, node{b, n}}
};
int main(){
A a(3, 4);
assert( a.n.val == 3 );
assert(&(a.n.next.next) == &(a.n)); // this assert fail and
assert( a.n.next.val == 4 ); // segmentation fault here
}
我得到的警告是gcc: warning: a temporary bound to ‘A::n’ only persists until the constructor exits [-Wextra]
. 我不相信警告是正确的,但它与后来的运行时错误一致。
我承认这个类是非传统的,但是,它怎么可能改变类内部的行为呢?
我错过了什么吗?
聚合初始化允许绑定对临时的引用(这会导致生存期延长(。 您的第一个示例是聚合初始化,因为node
是一个聚合。
但是,在构造函数成员初始值设定项列表中,将引用绑定到临时 (C++17 class.base.init/11( 的格式不正确。这是因为在那种情况下没有寿命延长,允许它不可避免地会产生一个悬而未决的参考。 在第二个示例中,node
不是聚合,因为它具有用户提供的构造函数。
相关文章:
- C++ 如何将关键字"friend"与两个类的成员函数一起使用 相互包含
- 与引用一起使用的列表,在用作成员时更改行为
- 在 c++ 中将模板与类一起使用时,类成员函数的答案错误?
- 将 PIMPL 习惯用法与成员函数模板一起使用(无需预先了解所有可能的数据类型)
- 如何将两个类成员函数与同一类中的另一个函数一起添加
- 如何将此指针与指向成员函数的指针一起使用
- 将指令与模板化成员函数一起使用
- 常量变量初始化仅与成员初始化列表一起工作
- 与const成员一起安排新的和班级的分配
- GCC 中的编译器错误,但在将 decltype 与具有尾随返回类型语法的模板化成员函数一起使用时没有 clang
- 将异步与多态成员函数一起使用
- 将GSL与C 一起使用时,如何避免静态成员函数
- boost :: Spirit :: Qi-与语法结构中的实例成员一起工作
- 如何将序列化方法添加到作为Windows数据结构的类成员中,以便在C++中与boost序列化一起使用
- 为什么点运算符(.)可以与私有类成员/方法一起使用
- 将在一行中声明的成员记录在一起,而不创建组
- 获取指向成员std::string::size的指针无法与libc++链接,但可以与libstdc++一起使用
- 如何将尾随返回类型与模板化类成员一起使用
- 与私人成员一起上课.这个代码出了什么问题
- 将 decltype 与虚拟成员函数指针一起使用