C++98/03可以使用初始化列表initializer_list进行初始化普通数组和POD类型(基本数据类型等,具体要看定义)
//直接初始化
int j(0);
struct A {
public:
A(int){}
}a(3);
//初始化列表
int ch[] = {1, 4, 5};
struct A{
int x;
int y;
} a = {1, 3};
list-initialization是C++11提供的新类型,定义在initializer_list头文件中。 用于表示任何类型对象的初始化。
C++11中,可以直接再变量名后跟初始化列表,进行对象初始化。
//因为STL都内置了把初始化列表initialzer_list当做参数的构造函数。
std::vector<int> v { 1, 2, 3, 4 };
template <class T>
class M{
public:
M(const std::initializer_list<T> &v) {
for (auto i : v) {
vec.push_back(i);
}
}
private:
std::vector<T> vec;
};
M<int> m{ 1, 2, 3, 4 };//注意:必须用花括号才是调用. 初始化可添加=,也可不添加。
M<int> m1(1,2,3,4);//error 这个调用的是拷贝构造函数,调用的是M(int a, int b, int c, int d)
int* a = new int[3] {1,2,3};
//返回值
struct Foo{
Foo(int, double) {}
}
Foo func(void){
return {113, 3.3};//等于返回Foo(113, 3.3)
}
如何区分一个类(class struct union)是否可以使用列表初始化来完成初始化工作?
要看这个类是否是一个聚合体(aggregate),首先看下C++中关于类是否是一个聚合体的定义:
- 无用户自定义构造函数。
- 无私有或者受保护的非静态数据成员
- 无基类
- 无虚函数
- 无{}和=直接初始化的非静态数据成员。
struct ST{
int x;
int k = 33;//不符合规则5
protected:
int y;//不符合规则2
static int z;
}
ST s {2,3,4};//error
std::initializer_list
std::initializer_list是一个轻量级的容器类型,内部定义了iterator等容器必须的概念。
有三个成员接口size(), begin(), end()
只能整体初始化或赋值
std::initializer_list<int> list = {1,2,3};
size_t n = list.size(); // n == 3
无法修改std::initializer_list中某一个元素的值,但是可以通过初始化列表整体修改
std::initializer_list<int> list;
list = {1,2,3};
size_t n = list.size(); // n == 3
list = {1,2,4,3};
size_t n = list.size(); // n == 4