✅ 简洁总结(适合背 + 理解):
对比项 | 指针(Pointer) | 引用(Reference) |
---|---|---|
是否可为空 | ✅ 可以为 nullptr | ❌ 引用必须绑定有效对象 |
是否能修改指向 | ✅ 可以重新指向别的对象 | ❌ 引用一旦绑定不可更改 |
语法使用 | 使用 * 解引用,& 取地址 | 像别名一样直接用,无需 * |
是否可嵌套 | ✅ 指针的指针(T** ) | ❌ 引用的引用不存在 |
是否可空判断 | ✅ 可以 if (ptr) | ❌ 引用本身不能判空 |
本质 | 保存地址的变量(内存中一块值) | 变量的别名(本质是编译器处理) |
💡 简单例子对比
✅ 指针:
int a = 10;
int *p = &a; // 指针指向a
*p = 20; // 改变a的值
p = nullptr; // 可以置空
✅ 引用:
int a = 10;
int &ref = a; // 引用绑定a
ref = 20; // 改变a的值
// ref = nullptr; // ❌ 错误,引用不能是空的
🔍 引用和指针的核心区别(深入讲)
1. 📛 引用不能为 null,指针可以
引用必须一开始就初始化,且永远绑定那个对象:
int &r; // ❌ 错,引用必须初始化
int *p = nullptr; // ✅ OK
2. 🔄 指针可以重新指向别的变量,引用不行
int a = 10, b = 20;
int *p = &a;
p = &b; // ✅ OK
int &r = a;
r = b; // ❌ 不是“绑定b”,而是把 b 的值赋给 a!
3. ✍ 引用更像别名,语法更简洁
void update_by_pointer(int *p) {
*p = 100;
}
void update_by_reference(int &r) {
r = 100;
}
调用时:
int x = 5;
update_by_pointer(&x); // 传地址
update_by_reference(x); // 传变量本身
4. 🚫 没有引用的引用
int a = 10;
int& r = a;
int&& rr = 10; // ✅ 右值引用(C++11)
int& &invalid = r; // ❌ 不允许引用的引用
🎯 面试这样回答:
指针和引用都可以间接访问对象,但引用是一个必须绑定对象的别名,不能为 null,也不能更换绑定对象;指针是变量,保存地址,可以为 null、可以重新指向其他对象。引用语法更简洁、更安全,适用于函数参数和返回值优化;指针适合更灵活的内存操作,比如动态分配、数组遍历、实现数据结构等。