c语言第八章.ppt
《c语言第八章.ppt》由会员分享,可在线阅读,更多相关《c语言第八章.ppt(56页珍藏版)》请在淘文阁 - 分享文档赚钱的网站上搜索。
1、易学易学C+C+配套电子教案配套电子教案内存里的快捷方式内存里的快捷方式指针指针易学易学C+C+第八章第八章告诉你,不能怕告诉你,不能怕 指针曾是大家公认的指针曾是大家公认的C+C+中最难掌握的内容,对中最难掌握的内容,对指针的熟悉程度能够反映出一个指针的熟悉程度能够反映出一个C+C+程序员的水程序员的水平。平。指针的概念本身并不复杂。遇到复杂情况时,用指针的概念本身并不复杂。遇到复杂情况时,用“剥洋葱剥洋葱”的方法将它细心分解,各个击破。的方法将它细心分解,各个击破。告诉你,不能怕!告诉你,不能怕!4/3/20234/3/20232220092009年年33月月99日更新日更新本章目标本章目
2、标 理解指针的概念理解指针的概念 掌握指针的声明和使用掌握指针的声明和使用 掌握取地址操作符掌握取地址操作符 掌握掌握NULLNULL 掌握指针的运算掌握指针的运算 掌握常量指针和指针常量掌握常量指针和指针常量 理解数组名的实质和指针数组理解数组名的实质和指针数组 掌握指针作为函数参数和函数返回值掌握指针作为函数参数和函数返回值 掌握堆内存空间的使用掌握堆内存空间的使用4/3/20234/3/20233320092009年年33月月99日更新日更新菜鸟的囧事快捷方式存储的是程序所在的位置,真正调用的是程序本身。快捷方式所占的空间很小,而程序所占空间可能很大。如果这个位置不存在或不正确,则会发生
3、错误。4/3/20234/3/20234420092009年年33月月99日更新日更新内存中的快捷方式内存中的快捷方式 在在C+C+中,有一种记录数据在内存中存储位置中,有一种记录数据在内存中存储位置(地址)的数据类型,称为指针(地址)的数据类型,称为指针(PointerPointer)。)。指针中并不存储所要使用的数据,但我们可以通指针中并不存储所要使用的数据,但我们可以通过对指针所指向内存区域的操作来实现对数据的过对指针所指向内存区域的操作来实现对数据的访问或修改。访问或修改。如果指针指向了一个不应该被修改的数据,而我如果指针指向了一个不应该被修改的数据,而我们对它进行操作,可能导致严重的
4、程序异常或系们对它进行操作,可能导致严重的程序异常或系统错误。统错误。4/3/20234/3/20235520092009年年33月月99日更新日更新指针的类型指针的类型 指针存储的是内存地址,而内存地址的长度通指针存储的是内存地址,而内存地址的长度通常是一致的(取决于计算机和操作系统)。因常是一致的(取决于计算机和操作系统)。因此不同类型的指针所占内存空间是一致的,通此不同类型的指针所占内存空间是一致的,通常为常为3232位,即位,即4 4字节。字节。指向不同数据类型的指针具有不同的操作。例指向不同数据类型的指针具有不同的操作。例如长整型占如长整型占4 4个字节,那么长整型指针读出的个字节,
5、那么长整型指针读出的数据就是数据就是4 4个字节的整数;而字符型指针读出个字节的整数;而字符型指针读出的数据则是的数据则是1 1个字节的字符。个字节的字符。4/3/20234/3/20236620092009年年33月月99日更新日更新指针变量的声明指针变量的声明 指针变量在使用前也必须声明,其格式为:指针变量在使用前也必须声明,其格式为:所指数据类型所指数据类型*指针变量名指针变量名;例如:例如:intint*iptriptr;/指向整型变量的指针变量指向整型变量的指针变量 当要声明多个指针变量时,必须在每个指针变量名前当要声明多个指针变量时,必须在每个指针变量名前加上加上*,如:,如:in
6、tint*iptr1,*iptr2,iptr3;*iptr1,*iptr2,iptr3;/iptr3/iptr3不是指针,而是整不是指针,而是整型型4/3/20234/3/20237720092009年年33月月99日更新日更新取地址操作符取地址操作符 取地址操作符为取地址操作符为&,可以用它获取变量或自,可以用它获取变量或自定义常量在内存中的地址,方法为:定义常量在内存中的地址,方法为:&变量或常量名变量或常量名 获取后的结果可以赋值给指针变量,但应获取后的结果可以赋值给指针变量,但应当保证数据类型的一致,例如:当保证数据类型的一致,例如:intint c=9;c=9;intint*iptr
7、iptr=&c;=&c;4/3/20234/3/20238820092009年年33月月99日更新日更新空指针空指针NULLNULL 在使用指针前,不对指针赋值是危险的。对于某在使用指针前,不对指针赋值是危险的。对于某些操作系统来说,可能导致严重错误(比如些操作系统来说,可能导致严重错误(比如Windows98Windows98)。)。空指针表示指针没有指向任何东西,对空指针进空指针表示指针没有指向任何东西,对空指针进行操作虽然也会引起错误,但相比之下没有那么行操作虽然也会引起错误,但相比之下没有那么严重。严重。NULLNULL和和nullnull是不同的,是不同的,C+C+是大小写敏感的,例
8、是大小写敏感的,例如:如:intint*iptriptr=NULL;=NULL;/iptriptr不指向任何内存区域不指向任何内存区域4/3/20234/3/20239920092009年年33月月99日更新日更新间接引用间接引用 对于指向有效空间的指针变量,我们可以用间接对于指向有效空间的指针变量,我们可以用间接引用操作符引用操作符*来获取或修改其数据。使用方法为:来获取或修改其数据。使用方法为:*指针变量名指针变量名例如:例如:intint i=3;i=3;intint*iptriptr=&i;=&i;/iptriptr指向指向i i*iptriptr=4;=4;/i/i的值会变成的值会变
9、成4 44/3/20234/3/2023101020092009年年33月月99日更新日更新指针的加减运算指针的加减运算 指针只能和整型数做加减法(包括整型常量、变指针只能和整型数做加减法(包括整型常量、变量的加减法以及增量或减量操作)。量的加减法以及增量或减量操作)。指针的加减法并不是在地址上加减,因为这可能指针的加减法并不是在地址上加减,因为这可能使原来的数据使原来的数据“破碎破碎”。指针的加减结果与所指向的数据类型有关,例如指针的加减结果与所指向的数据类型有关,例如当增减当增减i i时:时:新地址新地址=旧地址旧地址ii每个对应数据类型(常量或变每个对应数据类型(常量或变量)在内存中所占
10、字节数。量)在内存中所占字节数。4/3/20234/3/2023111120092009年年33月月99日更新日更新查看内存查看内存问题描述问题描述 某些内存地址的数据是可以被我们获取的,某些内存地址的数据是可以被我们获取的,假设这个输入的地址总是有效的,尝试用假设这个输入的地址总是有效的,尝试用指针将该地址之后的指针将该地址之后的6464个字节数据输出。个字节数据输出。当以当以1616进制方式输入或输出数据时,可以进制方式输入或输出数据时,可以使用使用hexhex控制符,例如:控制符,例如:coutcout hex 15;hex hex a;hex a;/输入输入1616进制数进制数4/3/
11、20234/3/2023121220092009年年33月月99日更新日更新指针操作练习指针操作练习运行结果运行结果4/3/20234/3/2023131320092009年年33月月99日更新日更新指针操作练习指针操作练习设计设计 输入:输入:8 8位位1616进制地址进制地址 输出:该地址及其之后的输出:该地址及其之后的6464个字节数据个字节数据 算法:用循环嵌套,每输算法:用循环嵌套,每输出出1616字节换行一次。用指字节换行一次。用指针加法读取下一个数据。针加法读取下一个数据。存储:一个整型变量供输存储:一个整型变量供输入地址,指针用于读取内入地址,指针用于读取内存数据,循环变量存数
12、据,循环变量2 2个个4/3/20234/3/2023141420092009年年33月月99日更新日更新指针操作练习指针操作练习编码编码#include#include#include#include using namespace std;using namespace std;intint main()main()intint address;address;coutcout hex address;hex address;/以以以以1616进制输入进制输入进制输入进制输入unsigned char*unsigned char*cptrcptr=(unsigned char*)(addr
13、ess);=(unsigned char*)(address);/类型转换为无符号字符指针类型转换为无符号字符指针类型转换为无符号字符指针类型转换为无符号字符指针for(for(intint i=0;i4;i+)i=0;i4;i+)coutcout 0 x setw(8)setfill(0)hex(0 x setw(8)setfill(0)hex(int)(cptrint)(cptr):;):;/以以以以1616进制输出进制输出进制输出进制输出for(for(intint j=0;j16;j+)j=0;j16;j+)coutcout setw(2)setfill(0)(unsigned set
14、w(2)setfill(0)(unsigned intint)*)*cptrcptr ;cptrcptr=cptr+1;=cptr+1;coutcout endlendl;return 0;return 0;4/3/20234/3/2023151520092009年年33月月99日更新日更新指针的关系运算指针的关系运算 指针可以进行关系运算,其中较为常用的指针可以进行关系运算,其中较为常用的是等于和不等于,它们用于判断两个指针是等于和不等于,它们用于判断两个指针是否指向了同一个地址。是否指向了同一个地址。在进行大于或小于判断时,指针数值较小在进行大于或小于判断时,指针数值较小的通常在存储器中的
15、地址位置靠前,数值的通常在存储器中的地址位置靠前,数值较大的在存储器中的地址位置靠后。较大的在存储器中的地址位置靠后。4/3/20234/3/2023161620092009年年33月月99日更新日更新常量指针常量指针 指向自定义常量的指针称为指向自定义常量的指针称为“常量指针常量指针”。常量指针相当于对内存的写保护,只能读取数据,但常量指针相当于对内存的写保护,只能读取数据,但是不能进行修改。是不能进行修改。定义常量指针的方法为:定义常量指针的方法为:const const 所指数据类型所指数据类型*指针变量名指针变量名;常量指针能够保护指针所指向的内存区域,但是不能常量指针能够保护指针所指
16、向的内存区域,但是不能保护指针本身。即指针可以指向内存中任意一片有效保护指针本身。即指针可以指向内存中任意一片有效区域。区域。4/3/20234/3/2023171720092009年年33月月99日更新日更新指针常量指针常量 指针本身是常量,称为指针本身是常量,称为“指针常量指针常量”,其声明格,其声明格式为:式为:指针类型指针类型*const const 指针常量名指针常量名=&=&变量名变量名;指针常量和整型常量、字符型常量类似,不能作指针常量和整型常量、字符型常量类似,不能作为左值,但是它的间接引用可以作为左值。为左值,但是它的间接引用可以作为左值。指针常量保护的是指针本身所指向的内存
17、地址位指针常量保护的是指针本身所指向的内存地址位置不变,但是该内存区域的数据却可以被修改。置不变,但是该内存区域的数据却可以被修改。4/3/20234/3/2023181820092009年年33月月99日更新日更新常量指针和指针常量的对比常量指针和指针常量的对比常量指针指针常量全称指向“常量”的“指针”“指针”本身是“常量”const位置在数据类型的前面在指针常量名前面保护所指向内存区域指针所指的地址左值指针本身可作左值指针间接引用可作左值4/3/20234/3/2023191920092009年年33月月99日更新日更新数组名的实质数组名的实质 数组名存储了数组首元素的地址,但是这个地址数
18、组名存储了数组首元素的地址,但是这个地址无法随意更改。因此数组名是一个指针常量。无法随意更改。因此数组名是一个指针常量。指针也可以用类似于数组下标的方式访问数据,指针也可以用类似于数组下标的方式访问数据,例如:例如:intint a6;a6;/声明数组声明数组intint*aptraptr=a;=a;/指针指向数组首元素指针指向数组首元素aptr1aptr1,aptr2aptr2与与*(aptr+1)(aptr+1),*(aptr+2)(aptr+2)等效,等效,同时也与同时也与a1a1,a2a2、*(a+1)(a+1),*(a+2)(a+2)等效。等效。4/3/20234/3/2023202
19、020092009年年33月月99日更新日更新指针数组指针数组 指针也是数据类型,因此指针变量也可以指针也是数据类型,因此指针变量也可以有数组。指针数组的每个元素就是一个指有数组。指针数组的每个元素就是一个指针。针。如果指针数组的每个元素都指向一个数组,如果指针数组的每个元素都指向一个数组,那么就可以用类似于二维数组的方式访问。那么就可以用类似于二维数组的方式访问。例如:例如:intint*a5*a5a04a04 a00 a00指针数组指向数组首元素的指针具体数组元素4/3/20234/3/2023212120092009年年33月月99日更新日更新指针与字符串常量指针与字符串常量 用字符串方
20、式初始化的字符数组可以直接用用字符串方式初始化的字符数组可以直接用coutcout输出其内容。数组名相当于指向首元素的指针,输出其内容。数组名相当于指向首元素的指针,因此指向字符数组(字符串方式)首元素的指针因此指向字符数组(字符串方式)首元素的指针也能直接用也能直接用coutcout输出其内容。输出其内容。字符串常量的本质也是指针常量,例如:字符串常量的本质也是指针常量,例如:char*a=“Hello”;char*a=“Hello”;/把指针常量赋给指针变量把指针常量赋给指针变量 多次出现相同字符常量的地址是否相同,取决于多次出现相同字符常量的地址是否相同,取决于编译器是否对此进行优化。编
21、译器是否对此进行优化。4/3/20234/3/2023222220092009年年33月月99日更新日更新字符串查找字符串查找问题描述问题描述 已知在已知在cstringcstring头文件中有一个字符串的比较函数头文件中有一个字符串的比较函数strcmpstrcmp,其函数原型为:其函数原型为:intint strcmp(conststrcmp(const char*s1,const char*s2);char*s1,const char*s2);当字符串当字符串s1s1和和s2s2相同时,则返回相同时,则返回0 0,否则返回非,否则返回非0 0。现有若。现有若干个字符串常量以指针数组的方式
22、存在,数组的每个元素干个字符串常量以指针数组的方式存在,数组的每个元素为指向字符串的指针。它们依次是为指向字符串的指针。它们依次是“Hello”Hello”,“China”China”,“World”World”,“School”School”,“Student”Student”,“C+”C+”。请。请使用使用strcmpstrcmp函数找到函数找到“Student”Student”字符串所在的下标。字符串所在的下标。4/3/20234/3/2023232320092009年年33月月99日更新日更新字符串查找字符串查找运行结果运行结果4/3/20234/3/2023242420092009年
23、年33月月99日更新日更新字符串查找字符串查找设计设计 输入:无输入:无 输出:输出:6 6个字符串以及查个字符串以及查找结果找结果 算法:用循环将各个字符算法:用循环将各个字符串输出,并依次调用串输出,并依次调用strcmpstrcmp函数,根据返回值函数,根据返回值得到查找结果得到查找结果 存储:一个指针数组用来存储:一个指针数组用来存储多个字符串,一个字存储多个字符串,一个字符指针用来存储查找内容,符指针用来存储查找内容,另有循环控制变量另有循环控制变量4/3/20234/3/2023252520092009年年33月月99日更新日更新字符串查找字符串查找编码编码#include#inc
24、lude#include#include using namespace std;using namespace std;intint main()main()char*array6=char*array6=Hello,China,WorldHello,China,World,“School”,“Student”,“CSchool”,“Student”,“C+”;+”;/想想为什么可以这样初始化?想想为什么可以这样初始化?想想为什么可以这样初始化?想想为什么可以这样初始化?char*key=“Student”;char*key=“Student”;/需要查找的内容需要查找的内容需要查找的内容需
25、要查找的内容intint i;i;coutcout 6 6个字符串分别是:个字符串分别是:个字符串分别是:个字符串分别是:endlendl;for(i=0;i6;i+)for(i=0;i6;i+)coutcout arrayiarrayi endlendl;coutcout Student Student所在下标为:所在下标为:所在下标为:所在下标为:;for(i=0;i6;i+)for(i=0;i6;i+)if(if(strcmp(arrayi,keystrcmp(arrayi,key)=0)=0)/判断两个字符串是否内容相同判断两个字符串是否内容相同判断两个字符串是否内容相同判断两个字符串
- 配套讲稿:
如PPT文件的首页显示word图标,表示该PPT已包含配套word讲稿。双击word图标可打开word文档。
- 特殊限制:
部分文档作品中含有的国旗、国徽等图片,仅作为作品整体效果示例展示,禁止商用。设计者仅对作品中独创性部分享有著作权。
- 关 键 词:
- 语言 第八
限制150内