指针就是内存的地址,访问不同的指针就是访问内存中不同地址中的数据。
定义指针:类型名 *标识符;
int *p1; //定义一个指向整型的指针,名字p1
char *p2; //定义一个指向字符的指针,名字p2
和指针相关的两个运算符&和*
&:取地址运算符;& 指针变量名
int a;
int *p = &a;
*:指针运算符;*指针变量名
int i;
int *p1 = &i;
int i2 = *p1+1;
此语句表示指针变量p1所指向变量i的值加1赋给变量i2。
初始化指针:数据类型 *指针名 = 地址名;
int a;
int *p;
int *q = &a;
p = &a; //等价p=q
# include <iostream>
using namespace std;
int main(){
int a=1,b=3;
int *p1,*p2;
p1 = &a;
p2 = &b;
cout<<"p1="<<p1<<" "<<"p2="<<p2<<endl; //输出p1和p2的地址
cout<<"a="<<a<<" "<<"b="<<b<<endl; // 输出变量a和b的值
cout<<"*p1="<<*p1<<" "<<"*p2="<<*p2<<endl; //用间接运算符取出地址p1和p2的值
return 0;
}
指针的运算
指针的运算就是地址的运算
# include <iostream>
using namespace std;
int main(){
int a=1,b=3;
int *p1,*p2;
p1 = &a;
p2 = &b;
cout<<"p1地址中的值:"<<*p1<<endl;
cout<<"p2地址中的值:"<<*p2<<endl;
cout<<"p1-1地址中的值:"<<*(p1-1)<<endl;
cout<<"p1地址中的值-1:"<<*p1-1<<endl;
return 0;
}
指针和数组
指针与一维数组
对于一个数组来说,数组的名称就是这个数组的首地址。数组名就是一个指针变量。
int array[10];
int *p;
//对指针变量赋值
p = &array[0];//p = array;
ch3_3.cpp
# include <iostream>
using namespace std;
int main(){
int array[10];
int i;
int *p;
cout<<"请输入10个数"<<endl;
for(i=0;i<10;i++){
cin>>array[i];
}
cout<<endl;
for(p=array;p<(array+10);p++){
cout<<*p<<" ";
}
return 0;
}
对以上程序for循环的输入用指针进行改进。
# include <iostream>
using namespace std;
int main(){
int array[10];
int i;
int *p;
p = array;
cout<<"请输入10个数"<<endl;
// for(i=0;i<10;i++){
// cin>>array[i];
// }
for(i=0;i<10;i++){
cin>>*(p+i);
}
cout<<endl;
for(p=array;p<(array+10);p++){
cout<<*p<<" ";
}
return 0;
}
动态空间管理
用来存放函数形参和函数内的局部变量,在编译时指定空间,函数调用时分配空间,在函数执行完后分配的空间由编译器自动释放。很多时候只有运行时才知道数据空间的需求量,这就需要动态地分配与释放内存空间,这部分空间叫做堆区。
堆区由new来申请分配空间,使用delete释放空间,如果忘记delete释放空间,会导致所分配的空间一直占着不放,导致内存泄漏。
1,new运算符:开辟指定大小的存储空间,返回该存储区的起始地址。
类型说明符 *指针变量名 = new 类型说明符;申请一个类型说明符大小的空间赋值给指针变量。
类型说明符 *指针变量名 = new 类型说明符[整型表达式];申请整型表达式乘以类型说明符大小的空间赋值给指针变量。
float *p1 = new float; //堆空间开辟一个float类型空间,并把其地址赋给p1;
float *p2 = new float[10]; //堆空间开辟10个float类型空间,并把其地址赋给p2;
2,delete运算符:释放new开辟的存储空间。
delete 指针变量名;
delete []指针变量名;
delete p1; //释放p1所指向的float型变量空间
delete []p2; //释放p2所指向的10个float型变量组成的数组空间。