C++中的值初始化和默认初始化
1、值初始化
顾名思义,就是⽤数值初始化变量。如果没有给定⼀个初始值,就会根据变量或类对象的类型提供⼀个初始值。对于int类型其值初始化后的值为0。
2、默认初始化:如果定义变量时没有指定初值,则变量被默认初始化。其初始值和变量的类型以及变量定义的位置相关。默认初始化类对象和默认初始化内置类型变量有所不同。
对于默认初始化内置类型变量来说:
1)定义在函数体之外的变量是全局变量,⼀般存储在全局区,存储在全局区的变量⼀般会执⾏值初始化。此时,其初始值和变量的类型有关。对于int类型其初始值为0,对于char类型其默认初始值为' '。例⼦如下:
#include <iostream>
using namespace std;
int i;
double d;
char c;
int main()
{
cout << "i = " << i << endl;
cout << "d = " << d << endl;
cout << "char" << c << "char" << endl;
system("pause");
return 0;
}
在VS2015中编译结果如下:
2)定义在函数体内部的是局部变量,其存储在栈区中,如果没有指定初值,那么该局部变量将不会被初始化,也就是说这个局部变量的值是未定义的,是个随机值。此时,如果不给这个局部变量赋值,那么就不能使⽤该局部变量,否则就会出错,注意这种情况是没有被初始化,既没有使⽤默认初始化也没有使⽤值初始化,没有初始化的值是不能使⽤的。例⼦如下:
#include <iostream>
using namespace std;
int main()
{
int i;
cout << "i = " << i << endl;
system("pause");
return 0;
}
在VS2015中编译结果如下:
对于默认初始化类对象来说:不仅在创建类对象时,要使⽤默认构造函数,⽽且类成员要没有类内初始值,类才会执⾏默认初始化。
如果是⾃定义的默认构造函数,不进⾏任何操作或者是编译器合成的默认构造函数,其成员变量经过默认初始化之后的初始化值和局部变量的初始值是⼀样的,即是随机值,但是可以使⽤(类普通成员变量也存在栈区)。例⼦如下:
#include <iostream>
#include <string>
using namespace std;
class Init
{
public:
int getA()
{
return a;
}
double getD()
{
return d;
}
char getC()
{
return c;
}
string getStr()
{
namespace是干嘛的return str;
}
private:
int a;
char c;
double d;
string str;
};
int main()
{
Init init;
cout << "a = " << A() << endl;
cout << "d = " << D() << endl;
cout << "ccc" << C() << "ccc" << endl;
cout << "str" << Str() << "str" << endl;
system("pause");
return 0;
}
在VS2015中编译结果如下:
对于string类型的成员变量是个空串,这可能和string类的内部实现有关。
3、默认初始化的出现场景。
1)当我们在块作⽤域内不使⽤任何初始值定义⼀个⾮静态变量或者数组时。数组和⾮静态变量它们的值都是随机值,但是数组可以使⽤,⽽⾮静态变量需要在赋值以后才能使⽤。例⼦如下;
#include <iostream>
using namespace std;
int main()
{
int a[5];
for (int i = 0; i < 5; i++)
{
cout << "数组元素值为:" << a[i] << endl;
}
system("pause");
return 0;
}
在VS2015下编译结果如下:
2)当⼀个类本⾝含有类类型的成员且使⽤合成的默认构造函数时。使⽤合成的默认构造函数那么该类和其类类型成员都会执⾏默认初始化。
3)当类类型的成员没有在构造函数初始值列表中显⽰地初始化时。说明该类类型成员会调⽤默认构造函数。
4、值初始化的出现场景
1)在数组初始化的过程中如果我们提供的初始值数量少于数组的⼤⼩时,剩余的为提供初始值部分就会执⾏值初始化。
#include <iostream>
using namespace std;
int main()
{
int a[5] = {1, 2, 3};
for (int i = 0; i < 5; i++)
{
cout << "数组元素值为:" << a[i] << endl;
}
system("pause");
return 0;
}
在VS2015下编译结果如下:
由结果可知,没有提供初始值的数组元素按照值初始化为了0。
2)当我们不使⽤初始值定义⼀个局部静态变量时。因为是静态的,所以该局部静态变量不再存储在栈区,⽽是存储在全局区。此时,就会根据类型进⾏设置该变量的初始值,即值初始化。例⼦如下:
#include <iostream>
using namespace std;
int main()
{
static int a;
static char c;
cout << "a:" << a << endl;
cout << "ccc" << c << "ccc" << endl;
system("pause");
return 0;
}
VS2015编译结果为:
3)当我们通过书写形如T()的表达式显⽰请求值初始化时,其中T是类型名(vector的⼀个构造函数只接受⼀个实参⽤于说明vector的⼤⼩),它就是使⽤⼀个这种形式的实参来对它的元素初始器继续值初始化)。
===》》》对于默认初始化,可以参考《C++ primer》P40页
===》》》对于值初始化,可以参考《C++ primer》P88页
===》》》对于默认初始化和值初始化的发⽣场景,可以参考《C++ primer》P262页
===》》》对于合成的默认构造函数,可以参考《C++ primer》P235页

版权声明:本站内容均来自互联网,仅供演示用,请勿用于商业和其他非法用途。如果侵犯了您的权益请与我们联系QQ:729038198,我们将在24小时内删除。