C++实例化结构错误,为什么不允许这样做?

C++ instansing a struct error, why isn't this allowed?

本文关键字:不允许 这样做 为什么 实例化 结构 错误 C++      更新时间:2023-10-16

我在程序中使用以下结构体:

struct terminator{
    int id;
    string type;
    union{
        terminator *next;
        int empty;
    };
};

main中有以下代码:

int main(){
    terminator root = {0, "", NULL};
    root = {0, "", NULL}; //NOT ALLOWED WHY? Trying to set to its original value.
}

这会给出以下错误信息:

g++ lab8.cc -std=c++11
lab8.cc: In function 'int main()':
lab8.cc:78:21: error: no match for 'operator=' in 'root = {0, "", 0}'
lab8.cc:78:21: note: candidates are:
lab8.cc:6:8: note: terminator& terminator::operator=(const terminator&)
lab8.cc:6:8: note:   no known conversion for argument 1 from '<brace-enclosed in
itializer list>' to 'const terminator&'
lab8.cc:6:8: note: terminator& terminator::operator=(terminator&&)
lab8.cc:6:8: note:   no known conversion for argument 1 from '<brace-enclosed in
itializer list>' to 'terminator&&'

但这是可以的:

int main(){
    terminator root = {0, "", NULL};
    root = *(new terminator);
    root.id=0;
    root.type="";
    root.next=NULL;
}

为什么会这样?有办法绕过它吗?

在第一种情况下,您正在初始化结构。

在第二种情况下,您试图赋值给已经声明的变量,除非您的编译器支持复合文字作为扩展,否则这将不起作用。(即使是这样,你也需要写
root = (terminator){ 0, "", NULL };

让它实际工作。)

如果你可以使用c++ 11(看起来你是这样做的),你还可以利用名为"初始化列表"的新特性,它的语法类似:

root = terminator{ 0, "", NULL };

你需要告诉编译器RHS的类型是terminator:

root = terminator{0, "", NULL};

terminator root = {0, "", NULL};行聚合初始化,这是在没有构造函数时允许的一种构造形式。这里的=并不意味着赋值。在c++ 11中,您可以使用大括号语法来构造terminator类型的匿名临时对象,然后您可以将其分配给root:

root = terminator{0, "", nullptr};