列表初始化
{} 初始化
在C++98中,标准允许使用花括号{}对数组或者结构体元素进行统一的列表初始值设定。
比如下方示例:
C++11扩大了用大括号括起的列表(初始化列表)的使用范围,使其可用于所有的内置类型和用户自定义的类型,使用初始化列表时,可添加等号(=),也可不添加
内置类型
以下三种写法一样
自定义类型
对于自定义类型同样适用
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 class Date { public : Date (int year, int month, int day) :_year(year) , _month(month) , _day(day) { cout << "Date(int year, int month, int day)" << endl; } private : int _year; int _month; int _day; }; int main () { Date d1 (2022 , 11 , 22 ) ; Date d2 = {2022 , 11 , 11 }; Date d3{ 2022 , 11 , 11 }; return 0 ; }
STL容器
stl容器同样支持如上操作,并且更加方便
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 int main () { vector<int > v1 = { 1 , 2 , 3 , 4 , 5 , 6 }; vector<int > v2 { 1 , 2 , 3 , 4 , 5 , 6 }; list<int > lt1 = { 1 , 2 , 3 , 4 , 5 , 6 }; list<int > lt2{ 1 , 2 , 3 , 4 , 5 , 6 }; vector<Date> v3 = {d1, d2, d3}; vector<Date> v4 = { { 2022 , 1 , 1 }, {2022 , 11 , 11 } }; string s1 = "11111" ; map<string, string> dict = { { "sort" , "排序" }, { "insert" , "插入" } }; initializer_list<pair<const string, string>> kvil = { { "left" , "左边" }, { "left" , "左边" } }; dict = kvil; return 0 ; }
std::initializer_list
1 2 3 4 5 6 int main () { auto li = { 1 ,2 ,3 ,4 }; cout << typeid (li).name () << endl; return 0 ; }
容器底层实现,如vector增加initializer_list参数的构造代码如下:
1 2 3 4 5 6 7 8 9 vector (initializer_list<T> li) : _start(nullptr ), _finish(nullptr ), _end_of_storage(nullptr ) { reserve (li.size ()) for (auto & e : li) { push_back (e); } }
总结
C++11以后,一切对象都可以使用列表初始化,但是建议普通对象还是用以前的方式初始化,容器如果有需求可以用列表初始化
变量类型推导
decltype
关键字decltype将变量的类型声明为表达式指定的类型
新增加容器
array
c语言数组越界读基本检查不出来,越界写是抽查
array可以检查出来越界
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 int main () { const size_t N = 100 ; int a1[N]; a1[N]; a1[N + 5 ] = 1 ; array<int , N> a2; a2[N]; a2[N] = 1 ; a2[N + 5 ] = 1 ; return 0 ; }
forward_list
单链表