C++ Primer 5 第二章 课后题练习 部分内容

C++ Primer 5课后题练习

关于变量初始值

std::string global_str;
int global_int;
int main()
{
	int local_int;
	std::string local_str;
}

string类型本身接受无参数的初始化方式,所以不论变量定义在函数内还是函数外都被默认初始化为空串。

对于内置类型int来说,变量global_int定义在所有函数体之外,默认初始化为0;而变量local_int定义在main函数内部,不被初始化,若程序试图拷贝或输出未初始化的变量,将遇到一个未定义的奇异值。

关于变量声明和定义的关系

C++语言支持分离式编译机制,声明使得名字为程序所知,一个文件如果想使用别处定义的名字则必须包含对那个名字的声明。而定义负责创建与名字关联的实体,还申请存储空间,可能为变量赋一个初始值。

extern int i = 10;//声明并定义
extern int j;//声明
int k;//声明并定义

关于引用

int &r = 10;//引用必须指向一个实际存在的对象而非字面值常量
int &v;//由于无法令引用重新绑定到另外一个对象,所以引用必须初始化

关于指针

#include<iostream>
int main()
{
	int i = 5, j = 10;
	int *p = &i;
	std::cout << p << " " << *p << std::endl;
	p = &j;
	std::cout << p << " " << *p << std::endl;
	*p = 20;
	std::cout << p << " " << *p << std::endl;
	j = 30;
	std::cout << p << " " << *p << std::endl;
	return 0;
}

指针和引用的主要区别

指针“指向”内存中的某个对象,引用“绑定到”内存中的某个对象,都实现了对其他对象的间接访问。主要有两个区别:

一、指针本身是一个对象,允许对指针赋值和拷贝,在其生命周期内可以指向不同的对象;引用不是一个对象,无法令引用重新绑定到另外一个对象。

二、指针无须在定义时赋初始值,和其他内置类型一样,在块作用域内定义的指针如果没有初始化,将拥有一个不确定的值;引用则必须在定义时赋初值。

如何判断指针指向一个合法的对象

书上的答案:一种合理的处理办法是把if(p)置于try结构中,当程序块顺利执行时,表示p指向了合法的对象;当程序块出错跳转到catch时,表示p没有指向合法的对象。

关于常量引用、常量指针和指向常量的指针的初始化方法

int i = -1, &r = 0;//非法,非常量引用r不能引用字面值常量
const int i = -1, &r =0;//合法,i是一个常量,r是一个常量引用,r可以绑定到字面值常量
const int &const r2;//非法,引用本身不是对象,因此不能让引用恒定不变
const int i2 = i, &r = i;//合法,i2是一个常量,r是一个常量引用
const int *const p3 = &i2;//合法,p3是一个常量指针,p3的值永不改变,即p3永远指向变量i2;同时,p3指向的是常量,即不能通过p3改变所指对象的值。
int i, *const cp;//非法,cp为常量指针,因其值不能改变,所以必须初始化
const int ic, &r = ic;//ic为常量,必须初始化
const int *const p3;//非法,需初始化
const int *p;//合法,但是p没有指向任何实际对象

关于顶层const与底层const

人家讲的挺好的,附上链接:https://blog.csdn.net/qq_19528953/article/details/50922303

在执行拷贝操作时,顶层const和底层const区别明显。顶层const不受影响,这是因为拷贝操作不会改变被拷贝对象的值。而对于底层const来说,拷入和拷出的对象必须具有相同的底层const资格,或者两个对象的数据类型必须能够转换。一般来说,非常量可以转换成常量,反之则不行。

关于的decltype

int a = 3, b = 4;
decltype(a) c = a;//相当于 int c = a;
decltype((b)) d = a;//相当于 int &d = a;
++c;
++d;
//程序结束时a,b,c,d都为4

decltype(a=b) d = a;//当参数是表达式时,推断出的类型是引用。所以d的类型为int&

auto和decltype的区别

#include<iostream>
#include<typeinfo>
int main()
{
	int a = 3;
	auto c1 = a;
	decltype(a) c2 = a;
	decltype((a)) c3 = a//c3为变量a的别名

	const int d = 5;//d为常量整数,含有顶层const
	auto f1 = d;//auto忽略顶层const,所以推断结果为整数
	decltype(d) f2 = d;//保留顶层const,f2为整形常量

	std::cout << typeid(c1).name() << std::endl;
	std::cout << typeid(c2).name() << std::endl;
	std::cout << typeid(c3).name() << std::endl;
	std::cout << typeid(f1).name() << std::endl;
	std::cout << typeid(f1).name() << std::endl;

	c1++;
	c2++;
	c3++;
	f1++;
	//f2++;
	//错误:f2是整形常量,不能执行自增操作
	std::cout << a << " " << c1 << " " << c2 << " "
			<< c3 << " " << f1 << " " << f2 <<std::endl;
	return 0;
}

 

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值