C++法则8:对于有引用成员的类,合成拷贝赋值运算符被定义为删除的。

C++法则8:对于有引用成员的类,合成拷贝赋值运算符被定义为删除的。

在 C++ 中,Rule of 8(法则 8)并不是一个官方术语,但通常指与特殊成员函数(如拷贝构造函数、拷贝赋值运算符、移动构造函数、移动赋值运算符等)相关的规则。这里提到的规则实际上是关于类中包含引用成员时,拷贝赋值运算符的行为

法则 8 的解释

如果一个类包含引用成员,那么编译器会自动将合成的拷贝赋值运算符(operator=)定义为 deleted(删除的)。

为什么?

  • 引用(T&)一旦初始化后就不能再绑定到另一个对象。因此,默认的拷贝赋值运算符(尝试逐个成员赋值)无法正确修改引用成员所引用的目标。

  • 如果允许默认的拷贝赋值,可能会导致意外的行为或违反引用的语义。

示例

#include <iostream>

class RefHolder {
public:
    int& ref;  // 引用成员
    RefHolder(int& x) : ref(x) {}
    // 编译器不会生成默认的拷贝赋值运算符(它会被定义为 deleted)
};

int main() {
    int a = 10, b = 20;
    RefHolder obj1(a);
    RefHolder obj2(b);

    // obj1 = obj2;  // 错误!拷贝赋值运算符是 deleted 的
    return 0;
}
  • 如果你尝试 obj1 = obj2;,编译器会报错,因为 RefHolder 的拷贝赋值运算符是 deleted 的。

如何解决?

如果类包含引用成员,并且你确实需要支持拷贝赋值,必须手动定义拷贝赋值运算符

class RefHolder {
public:
    int& ref;
    RefHolder(int& x) : ref(x) {}

    // 手动定义拷贝赋值运算符
    RefHolder& operator=(const RefHolder& other) {
        ref = other.ref;  // 注意:这里修改的是引用指向的值,而非引用本身
        return *this;
    }
};
  • 但要注意,这样并不会改变 ref 引用的对象,而是修改 ref 指向的值。

总结

  • 如果类有引用成员,合成的拷贝赋值运算符会被 deleted。

  • 如果需要拷贝赋值,必须手动定义。

  • 引用成员在赋值时不会改变绑定,只能修改被引用的值。

这个规则是 C++ 对象模型的一部分,确保引用语义的正确性。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值