18、有关指针,计算机是通过地址来找到某个变量的。在C语言中,用指针来表示内存地址,或者成为指针指向了内存地址,而如果恰好这个内存地址是某个变量的地止,那么又称“这个指针指向该变量”。只要在变量名前面加上&,就能获取该变量的地址。指针是一个unsigned类型的整数。
指针变量用来存放指针(或者可以理解为地址),这个关系和int型变量用来存放int型常量相同。可以把地址当做常量,专门定义一种指针变量来存放它。但是指针变量的定义和普通变量有所区别,它在某种数据类型后加*号来表示这是一个指针变量,例如:
int* p;
double* p;
char* p;
c程序员习惯 int *p;
而c++程序员习惯int* p;
如果有好几个同种类型的指针变量要同时定义,星号只会和第一个结合。下面的p1是int*型,而p2是int型
int* p1,p2;
int* p1,*p2,*p3;
19、给指针变量赋值的方式一般是把变量的地址取出来,然后赋给对应类型的指针变量
int a,b;
int* p1 = &a,*p2 = &b;
需要注意的是,int星号是指针变量的类型,而p才是变量名,所以&a是给p的而不是给星号p的。
把星号当做是一把开启房间的钥匙,将其加在p之前,星号p就可以把房间打开,获取变量a的值【星号是钥匙,p存着门牌号,a是房间里的东西,*p也是指地址中存放的元素,它俩等价】
20、指针变量也可以加减法,减法的结果就是两个地址偏倚的距离,对一个int星号型的指针变量来说,p+1是指p所指的int型变量的下一个int型变量地址。这个下一个是跨越了一整个int型(即4byte),因此如果是p+i,则是跨越了当前int型变量之后的第i个变量。
而且指针变量还支持自加自减。对于int* p;来说,int是它的基类型。double* q;,double是它的基类型。
21、c语言中,数组名可作为数组的首地址使用。假设现有一个int型数组,a[10]。则a==&a[0],例如
int a[10]={1};
int* p=a;
printf("%d\n",*p);
输出为1。a作为数组a的数组a的首地址&a[0],被赋值给指针变量p,因此输出 星号p其实就是输出a[0]。
前面提到过,指针变量可以进行加减法,结合这个知识点很容易可以推出a+i等同&a[i]。但是也应该注意,a+i其实是地址,如果要访问里头的东西,要加星号。使其变成 星号(a+i)之后,才与a[i]等价
#include
int main(){
int a[10];
for(int i = 0; i < 10; i++){
scanf("%d",a+i);
}
for(int i = 0; i < 10; i++){
printf("%d",*(a+i));
}
return 0 ;
}
22、由于指针变量还可以自增,所以还能枚举数组中的元素
int a[10]={1,2,3,4,5,6,7,8,9,10};
for(int* p = a; p < a+10; p++){
scanf("%d",*p);
}
23、指针的减法
#include
int main(){
int a[10]={1, 4, 9, 16, 25, 36, 49};
int* p = a;
int* q = &a[5];
printf("q = %d",q);
printf("p = %d",p);
printf("q-p = %d",q-p);
return 0;
}
q = 2686708
p = 2686688
q-p = 5
p和q分别是&a[0],和&a[5]。则q-p就是两个地址之间的距离。这个距离以int为单位,两个int型指针相减,等价于再求两个指针之间差了几个int
24、在使用指针变量作为函数参数时候,如果在函数中对地址中的内容进行改变,则原先的数据确实会被改变。【址传递】
【函数在接收参数的时候是值传递,值传递是相当于产生了一个副本,不会对原先的量进行变化】
void swap(int* a, int* b){
int temp = *a;
*a = *b;
*b = temp;
}
此时形参a存放的是&a,即为地址。而星号a存放的是地址里的内容。
有一种错误的写法
void swap(int* a, int* b){
int* temp = a;
a = b;
b = temp;
}
main函数对于传给swap函数的“地址”,其实是一个无符号整数。本身也只是值传递,对这个修改并不能对main函数里头的地址修改。
·
·
25、引用是c++中的强有力语法,相当实用。不采用指针,也能达到修改传入参数的目的。引用其实就是给原变量起了个“外号”,对引用变量的操作就是对原变量的操作。
书写位置和星号指针一样,但是考虑是别名的意思,因此一般写在变量前面。
#include
void change(int &x){
x = 1;
}
int main(){
int a = 10;
change(a);
printf("%d\n",x);
return 0;
}
输出是1.不管是否使用引用,函数的参数名和实际传入的参数名可以不同
注意:要把引用的&跟取地址运算符&区分开来,引用并不是取地址的意思。
26、指针的引用。
之前两个变量的效果但是失败了的那个例子,是因为对指针变量本身的修改没办法作用到原指针变量上。此处可用引用达到效果
#include
void swap(int* &a, int* &b){
int* temp = a;
a = b;
b = temp;
}
int main(){
int a = 1,b = 2;
int *p1 = &a, *p2 = &b;
swap(p1,p2);
printf("a = %d, b = %d \n",*p1,*p2);
return 0 ;
}
引用是产生变量的别名,对于常量无效。所以不可以以上不能直接写为swap(&a,&b);而用p1和p2存放&a和&b,然后把指针变量作为参数传入。