实验9指针 9.1指针的概念及基本运算 【实验目的】 1.理解指针的概念,掌握指针变量的定义和使用: 2.理解指针和地址间的关系: 3.掌握指针的基本运算: 4.掌握指针作为函数参数的方法: 【相关知识点】 1.指针变量的定义方式 指针变量的定义方式一般为: int *p; ∥定义单个整型指针变量 char *ch; ∥定义单个字符指针变量 2.指针变量的初始化 指针被定义后,必须将指针和一个特定的变量进行关联后,才可以使用指针。也就是说, 指针变量也要先赋值再使用,当然指针变量被赋的值应该是地址。假设有定义: int i,*p; 下面的语句可以对指针变量p赋值: p=&i; 该语句中的指针p被看做是指向变量ⅰ或包含变量i的地址,也就是将指针p和普通的整 型变量ⅰ关联起来,这是指针最常用的赋值方法。 另外,可使用语句: p=NULL; 来对指针赋初值,此时指针的值为NULL。常量NULL在系统文件stdio.h中定义,其值 为0,将它赋给指针时,代表空指针。C语言中的空指针不指向任何存储单元。 -167-
实验 9 指针 9.1 指针的概念及基本运算 【实验目的】 1. 理解指针的概念,掌握指针变量的定义和使用; 2. 理解指针和地址间的关系; 3. 掌握指针的基本运算; 4. 掌握指针作为函数参数的方法; 【相关知识点】 1. 指针变量的定义方式 指针变量的定义方式一般为: int *p; //定义单个整型指针变量 char *ch; //定义单个字符指针变量 2. 指针变量的初始化 指针被定义后,必须将指针和一个特定的变量进行关联后,才可以使用指针。也就是说, 指针变量也要先赋值再使用,当然指针变量被赋的值应该是地址。假设有定义: int i,*p; 下面的语句可以对指针变量 p 赋值: p = &i; 该语句中的指针 p 被看做是指向变量 i 或包含变量 i 的地址,也就是将指针 p 和普通的整 型变量 i 关联起来,这是指针最常用的赋值方法。 另外,可使用语句: p = NULL; 来对指针赋初值,此时指针的值为 NULL。常量 NULL 在系统文件 stdio.h 中定义,其值 为 0,将它赋给指针时,代表空指针。C 语言中的空指针不指向任何存储单元。 - 167 -
指针除了指向己有变量或常量的地址外,还可以通过malloc函数动态申请分配内存。 malloc函数的原型是: void *malloc(unsigned size) 其功能是在内存的动态存储区域中分配一连续空间,长度为sz心。若申请成功,则返回一 个指向所分配内存空间的起始地址的指针:若申请内存空间不成功,则返回NULL。 3.指针的基本运算 如果指针的值是某个变量的地址,通过指针就能间接访问那个变量,这些操作由取地址 运算符&和间接访问运算符*完成。此外,相同类型的指针还能进行赋值、比较和算术运算。 示例1: int *p,a=99; p=&a; printf("%d\n",*p); *p=100: printf("%d n",a), 在该示例中,语句 p=&a; 是将整型变量a的地址赋给指针变量p(注意使用了取地址运算符&),那么,*p就是取 得p中所保存的地址所指向的存储单元的值(注意使用了间接访问运算符*),也就是变量 的值。语句 *p=100 的作用是将p中所保存的地址所指向的存储单元的值改为100,也即变量a的值改为100。 另外,指针被定义并赋值后,就可以如同其他类型的变量一样进行赋值运算。 示例2: int a=99,*pl,*p2; pl=&a; p2=pl店 该示例将指针变量p1存放的地址值赋给指针变量p2。注意,只能将一个指针的值赋给另 一个相同类型的指针。 -168-
指针除了指向已有变量或常量的地址外,还可以通过 malloc 函数动态申请分配内存。 malloc 函数的原型是: void *malloc(unsigned size) 其功能是在内存的动态存储区域中分配一连续空间,长度为 size。若申请成功,则返回一 个指向所分配内存空间的起始地址的指针;若申请内存空间不成功,则返回 NULL。 3. 指针的基本运算 如果指针的值是某个变量的地址,通过指针就能间接访问那个变量,这些操作由取地址 运算符&和间接访问运算符*完成。此外,相同类型的指针还能进行赋值、比较和算术运算。 示例 1: int *p,a=99; p=&a; printf("%d\n",*p); *p=100; printf("%d\n",a); 在该示例中,语句 p=&a; 是将整型变量 a 的地址赋给指针变量 p(注意使用了取地址运算符&),那么,*p 就是取 得 p 中所保存的地址所指向的存储单元的值(注意使用了间接访问运算符*),也就是变量 a 的值。语句 *p=100; 的作用是将 p 中所保存的地址所指向的存储单元的值改为 100,也即变量 a 的值改为 100。 另外,指针被定义并赋值后,就可以如同其他类型的变量一样进行赋值运算。 示例 2: int a=99,*p1,*p2; p1=&a; p2=p1; 该示例将指针变量 p1 存放的地址值赋给指针变量 p2。注意,只能将一个指针的值赋给另 一个相同类型的指针。 - 168 -
4.指针作为函数参数的方法 指针作为函数的参数,主要是在函数定义时将指针变量作为形式参数,在函数调用时, 实际参数必须是地址表达式。 示例: #include <stdio.h> void main(void) { inta=99,b=100: void swap(int *pl,int *p2); swap(&a,&b); printf("%d %d n",a,b); } void swap(int *pl,int *p2) int temp; temp=*pl; *pl=*p2; *p2 =temp; } 该示例中的函数swp使用指针做参数,实现两个数的交换,其形式参数有2个,均为指 针变量。在mai中调用该函数时,使用两个整型变量的地址作为实际参数。使用指针做函数 的参数,传递的是变量的地址:不使用指针做参数时,传递的是变量的值。 5.指针与地址之间的关系 要学会使用指针,最重要的一点是必须深刻理解指针其实就是地址。仔细阅读下面的几 个示例程序,并输入到VC中编译、运行,查看程序的输出结果。 示例1:该程序简明地说明了变量在内存中的位置。 #include <stdio.h> -169-
4. 指针作为函数参数的方法 指针作为函数的参数,主要是在函数定义时将指针变量作为形式参数,在函数调用时, 实际参数必须是地址表达式。 示例: #include <stdio.h> void main(void) { int a=99,b=100; void swap(int *p1,int *p2); swap(&a,&b); printf("%d %d\n",a,b); } void swap(int *p1,int *p2) { int temp; temp = *p1; *p1 = *p2; *p2 = temp; } 该示例中的函数 swap 使用指针做参数,实现两个数的交换,其形式参数有 2 个,均为指 针变量。在 main 中调用该函数时,使用两个整型变量的地址作为实际参数。使用指针做函数 的参数,传递的是变量的地址;不使用指针做参数时,传递的是变量的值。 5. 指针与地址之间的关系 要学会使用指针,最重要的一点是必须深刻理解指针其实就是地址。仔细阅读下面的几 个示例程序,并输入到 VC 中编译、运行,查看程序的输出结果。 示例 1:该程序简明地说明了变量在内存中的位置。 #include <stdio.h> - 169 -
void main(void) { int i=10,j=20; char chl='a'.ch2='b': f1 loat f1=99,2=100; printf("整型变量i的地址:%d;整型变量j的地址:%dn",&i,&j)方 printf("字符变量chl的地址:%d;字符变量ch2的地址:%dn",&chl,&ch2; printf("浮点变量f1的地址:%d;浮点变量f2的地址:%dn",&f1,&f2); 示例2:该程序演示了指针变量的实质。首先,系统也对指针变量本身分配存储空间,其 次,它保存了某个存储单元的地址,通过指针变量可以访问该地址代表的存储单元。 #include <stdio.h> void main(void) { char ch='a',*pch; int i=10,*pi; pch=&ch; pi=&i; printf"字符变量ch的地址:%d;指针变量pch的地址:%dn",&ch,&pch; printf("整型变量i的地址:%d,指针变量pi的地址:%dn",&i,&pi); printf("字符变量ch的值:%c,指针变量pch的值:%dn",ch,pch: printf("整型变量i的值:%d;指针变量pi的值:%dn",i,pi); printf("指针变量pch所指向的存储单元的值:%cln",*pch); printf("指针变量pi所指向的存储单元的值:%dn",*pi); 示例3:该程序解释了函数参数值传递的原理。 #include <stdio.h> -170-
void main(void) { int i=10,j=20; char ch1='a',ch2='b'; float f1=99,f2=100; printf("整型变量 i 的地址:%d ;整型变量 j 的地址:%d \n",&i,&j); printf("字符变量 ch1 的地址:%d ;字符变量 ch2 的地址:%d\n",&ch1,&ch2); printf("浮点变量 f1 的地址:%d ;浮点变量 f2 的地址:%d\n",&f1,&f2); } 示例 2:该程序演示了指针变量的实质。首先,系统也对指针变量本身分配存储空间,其 次,它保存了某个存储单元的地址,通过指针变量可以访问该地址代表的存储单元。 #include <stdio.h> void main(void) { char ch='a',*pch; int i=10,*pi; pch=&ch; pi=&i; printf("字符变量 ch 的地址: %d; 指针变量 pch 的地址: %d\n",&ch,&pch); printf("整型变量 i 的地址: %d; 指针变量 pi 的地址: %d\n",&i,&pi); printf("字符变量 ch 的值: %c; 指针变量 pch 的值: %d\n",ch,pch); printf("整型变量 i 的值: %d; 指针变量 pi 的值: %d\n",i,pi); printf("指针变量 pch 所指向的存储单元的值: %c\n",*pch); printf("指针变量 pi 所指向的存储单元的值: %d\n",*pi); } 示例 3:该程序解释了函数参数值传递的原理。 #include <stdio.h> - 170 -
void swap(int x,int y) { int temp; printf("函数swap中,变量x的地址:%d;变量y的地址:%dn",&x,&y)方 printf("函数swap中,交换前:X=%d,y=%dn",Xy);方 temp-x,x可y,y=temp, printf("函数swap中,交换后:X=%d,y=%dn",X,y)方 void main(void) int a-3,b-4; printf("main函数中,变量a的地址:%d,变量b的地址:%dn",&a,&b printf("调用swap函数交换前:a=%d,b=%dn",a,b方 swap(a,b); printf("调用swap函数交换后:a=%d,b=%dn",a,b方 示例4:该程序解释了使用指针作为参数进行地址传递的过程及产生的结果。 #include <stdio.h> void swap(int *x,int *y) int temp: printf("函数swap中,指针变量x的地址:%d;指针变量y的地址:%dn",&x,&y)方 printf("函数swap中,指针变量x的值:%d,指针变量y的值:%dn",x,y): printf("函数swap中,交换前:*x=%d,*y=%dn",*x,*y); temp=*x;*x=*y;*y=temp; printf("函数swap中,交换后:*x=%d,*y=%dn",*x,*y)店 -171-
void swap(int x,int y) { int temp; printf("函数 swap 中,变量 x 的地址:%d; 变量 y 的地址:%d\n",&x,&y); printf("函数 swap 中,交换前:x=%d,y=%d\n",x,y); temp=x;x=y;y=temp; printf("函数 swap 中,交换后:x=%d,y=%d\n",x,y); } void main(void) { int a=3,b=4; printf("main 函数中,变量 a 的地址:%d; 变量 b 的地址:%d\n",&a,&b); printf("调用 swap 函数交换前:a=%d,b=%d\n",a,b); swap(a,b); printf("调用 swap 函数交换后:a=%d,b=%d\n",a,b); } 示例 4:该程序解释了使用指针作为参数进行地址传递的过程及产生的结果。 #include <stdio.h> void swap(int *x,int *y) { int temp; printf("函数 swap 中,指针变量 x 的地址:%d; 指针变量 y 的地址:%d\n",&x,&y); printf("函数 swap 中,指针变量 x 的值:%d; 指针变量 y 的值:%d\n",x,y); printf("函数 swap 中,交换前:*x=%d,*y=%d\n",*x,*y); temp=*x;*x=*y;*y=temp; printf("函数 swap 中,交换后:*x=%d,*y=%d\n",*x,*y); } - 171 -