1.引用语义和值语义
C++同时支持引用语义(reference semantics)和值语义(value semantics),并默认使用值语义。
1.1 定义
值语义:指对象在赋值或传递时,进行的是值得复制,每个对象都有自己独立的数据副本,赋值过后,操作源对象和目的对象互不影响。
引用语义:指对象在赋值或传递时,复制的是引用(指针或句柄),而不是实际的类型,因此多个引用可能指向同一个实际对象,通过其中一个引用修改对象时,其他引用也会看到这个变化。
1.2 代码示例
值语义示例
struct Point {int x, y;Point(int x, int y) : x(x), y(y) {}
};void modify(Point p) {p.x = 100; //修改副本,原对象不会受到任何影响
}int main() {point p1{1, 2};point p2 = p1; //值拷贝modify(p1); //p1的值未改变return 0;
}
引用语义示例
class Buffer {std::vector<int> data;
public:void fill(int value) { data.assign(1000, value); }
};void modify(Buffer& buf) {buf.fill(42); // 修改原对象
}int main() {Buffer buf1;Buffer& buf_ref = buf1; // 引用语义,buf_ref 是 buf1 的别名modify(buf1); // buf1 的内容被修改
}
在C++里,使用引用类型一定会得到引用语义,但非引用的类型并不一定以为这值语义,因为使用智能指针(std::shared_ptr)时,虽然智能指针本身是值语义,但是指向的对象是引用语义。也就是说,智能指针的值复制会增加引用计数,但实际指向的对象是共享的。
1.3 关键对比
特性 | 值语义 | 引用语义 |
---|---|---|
数据所有权 | 每个对象拥有独立数据副本 | 共享同一份数据,无独立副本 |
默认行为 | C++基本类型和类对象的默认行为 | 需显式使用指针、引用或智能指针 |
拷贝开销 | 可能高昂(深拷贝大对象) | 无拷贝(传递指针/引用) |
修改影响 | 仅影响副本 | 影响所有关联引用 |
典型应用 | 小型数据、隔离修改需求 | 大型数据、共享状态、多态 |