1. 指针
1.1 指针是什么
我们每定义一个变量,系统会自动的分配内存空间存储该数据,指针就是指向某个数据的内存地址。
1.2 定义和使用指针
-
指针的定义格式为:
数据类型 * 指针变量名 * 是指针运算符,作用是返回指定地址内的变量的值。 -
指针的使用格式为:
指针变量名 = & 变量 &为取地址符,用于返回操作数的地址。
代码示例:
int a = 3;
int * p;
p = &a; //这两句也可以写成一句,用int * p = &a;这样定义之后,p就是一个指针变量,它存储的就是整型变量a的地址。
- 指针的解引用:
我们可以通过指针的解引用方式来找到指针指向的内存。通过:
指针前加 * 的方式,找到指针指向的内存中的数据,例如:
int a = 4;
int * p = &a;
cout<<"*p = "<<*p<<endl;//会输出 *p = 4
此时,* p 就完全等于变量a,我们对 *p 进行赋值等操作,就等同于对变量 a 进行操作。例如:
*p++;
cout<<"a = "<<a<<endl;//输出 a = 5
*p+=5;
cout<<"a = "<<a<<endl;//输出 a = 10
1.2 指针所占内存空间
指针存放的是数据地址,一般为十六进制的一串数。
在32位操作系统中,占用4个字节;
在64位操作系统中,占用8个字节。用代码查询如下:
int b =10;
int * p = &b;
cout<<"指针占用的内存为:"<<sizeof(p)<<"个字节"<<endl;//会输出 指针占用的内存为4个字节
注意:对于X86的编程,一般都是32位操作系统。而X64则对于64位操作系统。
1.3 空指针
空指针就是指针变量指向内存中编号为0的空间。
用途:用于指针的初始化。
注意:空指针指向的内存是不可以访问的,即 *p 不可以访问。
初始化:
int * p;//等同于int * p = NULL;
1.4 野指针
野指针是指针变量指向非法的内存空间。比如:指针指向一个未定义的指针地址,程序中尽量避免这种操作。
例如:
int * p = (int *)0x1100;
cout<< *p <<endl;//抛出异常,读取访问权限冲突。
1.5 const 修饰指针
1.5.1 const修饰指针 - 常量指针
const修饰指针,就是在指针前面加一个 const 进行限定。此时指针的指向可以修改,指针指向的值不可以修改。
使用格式:
const int * p = &a;const -(等同于)- 常量,所以 const + * 就是:常量指针。
const后面是 * ,所以对 *p 就不能改变,即不能改变 a 的值。
常量指针,即,常量地址,可以是一类常量的地址,地址可以改变,但常量不会变,所有地址指向的值是一样的。
1.5.2 const修饰常量 - 指针常量
const修饰常量,就是在变量面前加一个 const 进行限定,const +变量就变成了常量。此时指针的指向不可以修改,指针指向的值可以修改。
使用格式:
int * const p = &b;const -(等同于)- 常量,所以 * + const 就是:指针常量。
cosnt 后面是 p ,所以对 指针(地址) 就不可以修改,即不能再对 p 进行 & 操作。
指针常量:即地址常量,地址是个常量,所以地址(指针)就不会改变,但可以对地址指向的值进行任何操作。
1.5.3 const既然修饰指针又修饰常量
当cosnt既修饰指针,又修饰变量时,指针指向的地址和指向的值都不能进行修改了。
使用格式:
const int * const p = &c;指针指向的地址和的值都不能进行修改了
2. 指针和数组
2.1 定义
当我们定义一个数组时,系统会在内存中为其分配一个存储空间,,对数组来说,数组名就是数组在内存中的首地址,。定义一个指针变量,让它指向数组的首地址,则该指针就指向了这个一维数组。
int arr = { 1,2,3,4,5,6,7,8,9 };
int * p = arr;//arr就是数组的首地址
cout << p << endl;
2.2 指针自加减运算
上面指针p 所指向地址也是数组中第一个元素的地址,如果我们要指向数值中的第二个元素,就可以用 p++ 进行自增,
p++;
cout << p << endl;//输出数组中第二个元素的地址
cout << *p << endl;//输出数组的第二个元素
使用 p-- 则会输出是上一个数组元素。我们可以用循环加 p++ 将数组的每个指针都打印出来。 p+0 ~ p+8 就表示了数组中9个元素的地址。
int * p2 = arr;
for(int i = 0 ; i < 9 ; i++){
cout << p << endl;
p++;
}
2.3 指针与二维数组
对于一个二维数组如下:
int a[3][4] = {
{1 ,2 ,3 ,4}
{5 ,6 ,7 ,8}
{9,10,11,12}
}
定义一个指针 p3 指向这个二维数组:
int * p3 = a[0];
a[0] 既可以表示二维数组的首地址,a[0]也可以表示数组第0行的首地址,a[0] 还可以表示第0行第0列的数组元素的的首地址。
a[0]+n 是第0行第n个元素地址。
&a[n] 是第n行的首地址。
&a[n]+m 是第n行第m个元素的地址。