C++哪些运算符不能被重载?
在 C++ 中,大多数运算符都可以通过重载来自定义它们的行为,但有一些运算符是❌不能被重载的,这是出于语言语义、逻辑一致性或安全性考虑。
❌ 不能被重载的运算符(共 6 个)
运算符 | 说明 |
---|---|
. | 成员访问运算符(如 obj.member ),无法重载 |
.* | 成员指针访问运算符(如 obj.*ptr ) |
:: | 作用域解析运算符(如 std::cout ) |
sizeof | 求对象/类型大小 |
typeid | 类型识别运算符(用于 RTTI) |
? : | 三目运算符(三元选择符) |
⚠️ 补充说明
1. .
和 .*
为什么不能重载?
- 这些运算符和对象成员访问密切相关,重载会破坏语义清晰性。
- 如果想自定义访问行为,可以通过重载
operator->
间接实现。
2. ::
是作用域解析,必须在编译阶段解析,无法重载。
3. sizeof
和 typeid
是 编译期操作符,依赖类型信息,不能用于运行时多态行为。
4. ? :
是一个控制结构(不是函数调用),语法和语义复杂,不允许重载。
✅ 常见可重载的运算符(对比理解)
类别 | 运算符举例 | ||
---|---|---|---|
算术 | + - * / % | ||
比较 | == != < > <= >= | ||
逻辑 | `&& | !` | |
位运算 | `& | ^ ~ << >>` | |
赋值相关 | `= += -= *= /= %= &= | = ^=` | |
自增自减 | ++ -- | ||
下标 | [] | ||
函数调用 | () | ||
指针访问 | -> (注意:不是. ) | ||
地址/解引用 | & * | ||
输入输出 | << >> (通常用于流操作) |
🧠 记忆口诀(不能重载的运算符):
“点、指针、双冒号,大小类型三目巧。”
—— 即.
、.*
、::
、sizeof
、typeid
、?:
不能重载。