如果我有一个指向具有重载下标运算符([]
)的对象的指针,为什么我不能这样做:
MyClass *a = new MyClass();
a[1];
但必须这样做:
MyClass *a = new MyClass();
(*a)[1];
答案 0 :(得分:16)
这是因为你不能为指针类型重载运算符;你只能重载一个操作符,其中至少有一个参数(操作数)是类类型或枚举类型。
因此,如果您有一个指向某个类类型的对象的指针,该对象重载了下标运算符,则必须取消引用该指针才能调用其重载的下标运算符。
在您的示例中,a
的类型为MyClass*
;这是一个指针类型,因此使用指针的内置operator[]
。当您取消引用指针并获得MyClass
时,您有一个类类型对象,因此使用了重载的operator[]
。
答案 1 :(得分:7)
因为a
是指向MyClass而不是MyClass的类型指针。更改语言以支持您期望的使用会使许多其他语言语义中断。
您可以从中获得所需的语法结果:
struct foo {
int a[10];
int& operator [](int i) { return a[i]; }
};
main() {
foo *a = new foo();
foo &b = *a;
b[2] = 3;
}
答案 2 :(得分:3)
简单地说,使用a[1]
a
指针被视为包含数组的内存,并且您正在尝试访问数组中的第二个元素(不存在)。
(*a)[1]
强制首先在指针位置(*a)
获取实际对象,然后在其上调用[]
运算符。
答案 3 :(得分:1)
好消息。你也可以......
A->操作符[](1);
要添加首选答案,请将运算符重载视为重载函数。
当重载类的成员函数时,请记住指针不属于该类类型。