2020年3月29日
练习进度
2.9
a. 不能在输入时定义变量
b. int i={3.14}
; 会报错或警告,尽量不要用列表初始化可能会强制类型转换的值。
2.30 & 2.31
const int v2=0; //顶层const
int v1=v2;
int *p1=&v1,&r1=v1;
const int *p2=&v2,*const p3=&i,&r2=v2;
//p2底层const,p3右顶层const左底层const,r2底层const
r1=v2; //合法,此时的r1相当于v1,顶层const拷贝不受影响
p1=p2; //不合法,p1不是常量,p2是底层常量,这个问题我有点晕
p2=p1; //合法
p1=p3; //不合法
p2=p3; //合法
知识点记录
2.2 变量
-
何为对象?
通常情况下, 对象是指一块能存储数据并具有某种类型的内存空间。 -
列表初始化
用{}进行初始化 -
赋值和初始化的区别
初始化不是赋值, 初始化的含义是创建变量时赋予其一个初始值,而赋值的含义是把对象的当前值掠除,而以一个新值未替代。 -
全局算数类型变量的默认初值一般为0
-
声明与定义
定义申请空间,只能出现一次
声明不申请空间,可以出现多次
可以用extern
声明:extern int i;
,但是不能显式初始化,显示初始化的声明即是定义
对声明和定义的区分和理解主要是为了分离式编译 -
C++是一种静态类型(statically typed)语言,在编译阶段检查类型(type checking)。
-
作用域——全局作用域、块作用域,作用域的嵌套
2.3 复合类型
复合类型指的是:基于其他类型定义的类型。
常见复合类型:引用和指针。
引用
- 定义引用
int a=0;
int &a_ref=a;
- 引用在定义时必须赋初值,而且只能用对象赋值,不能用字面值赋值。
- 引用相当于其初值对象的别名,对引用的操作都会反映到初值对象上。
- 引用不是对象,不能更改绑定的对象,也不存在引用的引用。
指针
- 定义指针
int a=0;
int *p1; //定义时不赋初值
p1= &a; //赋值
int *p2=&a; //定义时赋初值
- 访问指针指向的对象
cout<<*p1; //对*p1操作相当于直接对a操作
*p1=10;
cout<<a;
- 指针的初值可以是0,nullptr,NULL,其他对象的地址,或者没有初值。
- void* 指针可以存放任意对象地址
- 指向指针的指针
int **p3=&p1;
cout<< **p3<<endl; //输出值为a的值10
- 指向指针的引用
int *&r=p1; //r是指针p1的引用
*r=0; //将a置0
要理解r
的类型到底是什么,最简单的办法是从右向左阅读r
的定义。离变量名最近的符号(此例中是&r
的符号&
)对变量的类型有最直接的影响,因此r
是一个引用。声明符的其余部分用以确定r
引用的类型是什么,此例中的符号*
说明r
引用的是一个指针。最后,声明的基本数据类型部分指出r
引用的是一个int
指针。
2.4 const
- const在定义时必须初始化
- 默认状态下,const对象仅在文件内有效
如果想在多个文件之间共享const 对象,必须在变量的定义之前添加extern关键字。在其他文件声明时也要加extern。 - const引用
const常量 只能被 const常量引用 所引用,但是
const常量引用 可以引用 非const变量(此时不能通过常量引用修改该变量的值)
注意:初始化常量引用时可以使用任意表达式做为初始值,只要该表达式的结果能转换成引用类型即可。 - 指向常量的指针(pointer to const)
与常量引用类似,
const常量只能用指向常量的指针存放地址,但是
指向常量的指针也可以存放变量地址
const double pi=3.14;
const double *ptr = π
- const指针
- 常量指针与指向常量的指针不同,定义为:
double pi=3.14;
double *const ptrc = π
常量指针必须在定义时初始化,这是他跟一般指针的显著区别
- 顶层const:本身是常量不可改变
底层const:指向的对象是常量 - constexpr不是十分理解