Warning: file_get_contents(/data/phpspider/zhask/data//catemap/6/cplusplus/154.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
&引用;你可以';t向前声明重载运算符的类&&引用;? 谷歌C++风格指南中,有一段有一个奇怪的声明:_C++_Gcc - Fatal编程技术网

&引用;你可以';t向前声明重载运算符的类&&引用;? 谷歌C++风格指南中,有一段有一个奇怪的声明:

&引用;你可以';t向前声明重载运算符的类&&引用;? 谷歌C++风格指南中,有一段有一个奇怪的声明:,c++,gcc,C++,Gcc,超载也有令人惊讶的作用 后果。例如,你不能 前向声明重载的类 操作员& 这似乎不正确,我还没有找到任何导致GCC出现问题的代码。有人知道那句话指的是什么吗?编辑以说明评论: 这是一个猜测,但向前声明的主要原因之一是能够声明指向该类的指针。在定义之前,编译器必须对类进行假设——例如,指针的大小 是否可以通过重载运算符来更改T*的大小&对于T?(编辑:评论员——我想不是)——但是 重载运算符违反了什么假设-,它如何更改类 这里有一个方法 我可以写: class A; void f(A& x

超载也有令人惊讶的作用 后果。例如,你不能 前向声明重载的类
操作员&

这似乎不正确,我还没有找到任何导致GCC出现问题的代码。有人知道那句话指的是什么吗?

编辑以说明评论:

这是一个猜测,但向前声明的主要原因之一是能够声明指向该类的指针。在定义之前,编译器必须对类进行假设——例如,指针的大小

是否可以通过重载运算符来更改T*的大小&对于T?(编辑:评论员——我想不是)——但是

重载运算符违反了什么假设-,它如何更改类

这里有一个方法

我可以写:

class A;

void f(A& x) {
    A* xPointer = &x;
}

如果运算符&()重载,则这有一个新的含义,编译器可能认为它可以为它生成代码,但这是错误的。

我也没有听说过它,但这可能会为重载前后的同一代码提供混淆的结果:

#include <iostream>

class Foo;

void bar (Foo& foo) {
    std::cout << &foo << std::endl;
}

class Foo {
public:
    bool operator & () { return true; }
};

void baz (Foo& foo) {
    std::cout << &foo << std::endl;
}

int main () {
    Foo foo;

    bar(foo);
    baz(foo);

    return 0;
}

尽管还有其他原因让你无论如何都不会这么做——重载地址不能很好地处理stl或许多通用代码。

我认为这句话不准确。和其他答案一样,我在这里猜测。首先,我想他们指的是。即:

int x = 5;
int* p = &x; // unary &
if (x & 1)   // binary &
可以向前声明所需的任何类。但是,如果类重载一元运算符&,并且您在指向其中一个对象的指针上调用一元运算符&,您可能会得到不一致的行为(有时您只会获取地址,有时您会调用重载的方法)。这很容易变成几乎不可能调试的东西


我很高兴fizzer实际上查看了该标准,而不仅仅是猜测。

5.3.1标准中有“可以获取不完整类型的对象的地址,但是如果该对象的完整类型是一个类类型,该类类型将运算符(())声明为成员函数,那么行为是未定义的(不需要诊断)。”


我也不知道这一点,但正如另一张海报所指出的,很容易看出它是如何导致编译器生成错误代码的。

措辞不清楚,您当然可以向前声明类-但规则显然采取了这样的立场:如果类重载
运算符&
,您“不应该”


类似的规则也存在于其他编码标准中,例如规则159规定不应重载
运算符&

由于运算符重载的能力,boost库提供了查找类的实际地址的功能。我并不是建议您重载运算符&,但如果需要,可以提供帮助。

我相信指针的大小总是相同的(这就是为什么编译器可以假定大小…),除了指向成员函数的指针之外,它们不是传统意义上的真正“指针”。是的,我想是的,我只是试着从一个前提开始,向前声明一个类型的目的是为了让编译器可以在没有完整声明的情况下对它进行一些假设。让操作符&.I更新一个例子,说明后面定义操作符时违反了什么假设&Yes-特别是不允许使用的重载操作符和定义。看起来声明本身是合法的,只要你从不使用它,或者只是用它来声明引用。也许它并没有被标准“禁止”,但根据是否提供了类/结构的定义,它的结果是不可靠的。正如fizzer所指出的,这是未定义的行为。从来都不好。
int x = 5;
int* p = &x; // unary &
if (x & 1)   // binary &