指针的概念
系统给虚拟内存的每个存储单元分配了一个编号。从0x00 00 00 00 到0xff ff ff ff
这个编号称为地址。
指针就是地址。
指针变量:是个变量,用来存放一个地址。
1、无论什么类型的地址,都是存储单元的编号,在32位平台下都是4个字节。即任何类型的指针变量都是4个字节大小。
2、对应类型的指针变量,只能存放对应类型的变量的地址。
指针是一个地址,而指针变量是存放地址的变量。
指针变量的定义方法
1、简单的指针变量
数据类型 *指针变量名;
c
int *p;//定义了一个指针变量p
在定义指针变量的时候*时用来修饰变量的,说明变量p是个指针变量。变量名是p。
2、关于指针的运算符
&取地址、*取值
c
int a = 0x1234abcd;
int *p;
p = &a; //把a的地址给p赋值,&是取地址符号。
int num = *p;//*p代表取值,就相当于把a的值给了num,和num=a效果一样。
p保存了a的地址,也可以说p指向了a。
c
int * pointer_1=&a,*pointer_2=&b;
说明:在定义指针变量时要注意:
(1)指针变量前面的""表示该变量的类型为指针型变量。指针变量名是pointer_1和
pointer_2,而不是 pointer_1和 pointer_2。这是与定义整型或实型变量的形式不同的。
上面程序不应写成:"*pointer_1=&a;"和"pointer_2=&b;"。因为a的地址
是赋给指针变量pointer_1,而不是赋给pointer_1(即变量a)。
指针的大小
*代表的是该变量是指针型变量。
p1是指针变量,存储的是地址,大小位32位系统4字节大小,固定不变。
前边的类型修饰符表明地址存储的数据类型。
c
char* p1;
short int* p2;
int* p3;
long int* p4;
float* p5;
double* p6;
通过指针引用数组
一个变量有地址,一个数组包含若于元素,每个数组元素都在内存中占用存储单元,它们都有相应的地址。指针变量既然可以指向变量,当然也可以指向数组元素(把某一元素的地址放到一个指针变量中),所谓数组元素的相针就是数组元素的地址。
引用
c
int a[10]={1,3,5,7,9,11,13,15,17,19};//定义a为包含10个整型数据的数组
int * pi;//定义p为指向整型变量的指针变量
p=&a[0];//把a[0]元素的地址赋给指针变量p
p=a; //p的值是数组a首元素(即a[0])的地址
注意:数组名不代表整个数组,只代表教组首元素的地址。上述"p=a;"的作用是"把
a数组的首元素的地址赋给指针变量p",而不是"把数组a各元素的值赋焓p"。
取值
c
*p;//是a[0]的值。
*a;//是a[0]的值。
*(p+1);//是a[1]的值。
*(a+1);//是a[1]的值。
如果指针变量p已指向数组中的一个元素,则p+1指向同一数组中的下一个元
素,p-1指向同一数组中的上一个元素
指针运算
做减法的护的结果是两个指针之间有多少个元素。
c
int a[10] = { 1,3,5,7,9,11,13,15,17,19 };
int* p, * p1;
p = a;
p1 = &a[3];
printf("%d", p1-p);
指针数组
数组中元素位相同类型的指针变量。
定义方式: int *p[5];
c
int* p[5];
int a = 100;
int b[10] = { 1,2,3,4,5,6,7,8,9,0 };
printf("%d\n", sizeof(p));//指针数组的大小
p[0] = &a;//数组0位置的指针变量指向a
printf("%p\n", p[0]);
printf("%p\n", &a);
printf("%d\n", *p[0]);
p[1] = &b[2];
printf("%d\n", *p[1]);
c
//hello、china等并不是存放在数组中,而是文字常量区中
//name[0]存放的是hello字符串的首地址。
char *name[5] = {"hello", "china", "beijing", "test"};
for (int i = 0; i < 4; i++)
{
printf("%s\n", name[i]);
}
指针的指针
指针的指针,即指针的地址。
c
int a = 100;
int *p;
p = &a;
int **p1;//*p1表示是一个指针,存放int*类型。
p1 = &p;
int ***p2;//*p2表示是一个指针,存放int**类型。