2014-02-27 104 views
2
struct ListNode { 
    int val; 
    ListNode *next; 
    ListNode(int x) : val(x), next(nullptr) { } 
}; 

这是ListNode的定义。 ListNode dummy{-1, head};是什么意思?什么是“ListNode dummy {-1,head};”意思?

+2

这不应该编译。 'ListNode'不是一个聚集(它有一个用户提供的构造函数),所以'dummy'不能使用聚合初始化来初始化,并且它没有带两个参数的构造函数。 – chris

+0

不,不是。 'ListNode'有一个用户提供的构造函数,所以它不是一个聚合,也不具备聚合初始化的资格。此外,它没有初始化列表构造函数,也没有可以接受两个参数的构造函数。 – Brian

+0

@nneonneo不,它不是。 – Borgleader

回答

4

这就是列表初始化,这是一种用于初始化C++ 11中引入的对象的相当新的语法。

在这种情况下,这是一个错误。由于该类有用户提供的构造函数,因此只能使用构造函数进行初始化;这个初始化需要一个构造函数,它带有两个不存在的参数。如果有一个合适的构造,就像

ListNode(int val, ListNode* next) : val(val), next(next) { } 

那就用它来初始化对象,传递的价值观-1head作为构造函数的参数。

如果类没有声明构造函数(或只是声明删除或默认的),使之成为一个,那么这将执行聚合初始化,初始化第一个成员val-1,和第二构件nexthead。但它不是一个聚合,所以这不会发生。

+0

如果编译的话,我假定在这种情况下,使用的特定编译器允许类似于聚合初始化的东西,作为语言的扩展。 (只要它发出警告,这样做是合法的。) – Brian

+0

我对于这种迂腐行为感觉不好,但是构造函数是'ListNode()= default;',它可以在不使用构造函数的情况下被初始化。此构造函数不是用户提供的,因此可以使用聚合初始化,并且聚合初始化不使用构造函数。 – chris

+0

@chris:确实。我已经让这门语言变得更具学生友好性,希望不会混淆含义太多。 –

1

此施工句式

ListNode dummy{-1, head}; 

定义了名称虚设类型ListNode的对象,并利用支撑初始化列表作为初始值设定。

编译器搜索具有两个参数的类构造函数,类定义中没有这样的构造函数只有构造函数具有一个参数。所以编译器会发出一个错误,它没有找到合适的构造函数。

我想你alread看到下面的结构

int a[] = { 1, 2, 3 }; 

其实这种结构

ListNode dummy{-1, head}; 

是一样的。你可以把它写成

ListNode dummy = {-1, head}; 

不同的是,类ListNode具有用户定义的构造和作为结果,编译器会寻找一个合适的构造函数与类两个参数。

如果类有构造

ListNode(int x, ListNode *node = nullptr) : val(x), next(node) { } 

代替

ListNode(int x) : val(x), next(nullptr) { } 

那么代码片段将被successfuly编译,因为这个修改的构造函数被调用。