第八章 善于使用指针(习题)
1、输入3个整数,要求按由小到大的顺序输出:
#include <stdio.h> void swap(int *p_a,int *p_b) // 比较两个数的函数 { int temp; if(*p_a>*p_b) { int temp=*p_a; *p_a=*p_b; *p_b=temp; } } void sort(int *pt1,int *pt2,int *pt3) // 比较三个数的函数 { if(*pt1<*pt2) { swap(pt1,pt2); //通过指针进行指向空间内的数据交换 } if(*pt1<*pt3) { swap(pt3,pt1); } if(*pt2<*pt3) { swap(pt3,pt2); } } int main() { int a,b,c; int *p1,*p2,*p3; p1=&a;p2=&b;p3=&c; // 获取每个变量空间的地址 printf("Please enter three numbers:\n"); scanf("%d,%d,%d",&a,&b,&c); sort(p1,p2,p3); printf("a=%d,b=%d,c=%d\n",a,b,c); return 0; }
2、输入3个字符串,要求按由小到大的顺序输出:
#include <stdio.h> #include <string.h> int main() { char str1[32],str2[32],str3[32]; char *p_s1=str1,*p_s2=str2,*p_s3=str3; printf("Please enter three string:\n"); scanf("%s %s %s",p_s1,p_s2,p_s3); if(strcmp(p_s1,p_s2)>0) { char *tmp=p_s1; p_s1=p_s2; p_s2=tmp; } if(strcmp(p_s1,p_s3)>0) { char *tmp=p_s1; p_s1=p_s3; p_s3=tmp; } if(strcmp(p_s2,p_s3)>0) { char *tmp=p_s2; p_s2=p_s3; p_s3=tmp; } printf("%s %s %s\n",p_s1,p_s2,p_s3); // system("pause"); return 0; }
#include <stdio.h> #include <string.h> int main() { char str[3][32]; char *p[3]; // 指针数组变量 printf("Please enter three strings:"); int i; for (i=0; i<3; i++) { p[i]=str[i]; // 分别把str[0],str[1],str[2]的首地址给指针数组 scanf("%s",p[i],32); //后边的数字限制缓冲区边界,防止缓冲区溢出访问越界 } //让p[0]和p[1]/p[2]分别进行比较,找出最大的字符串,i+1之后,则让p[1]和p[2]进行比较,找出第二大 //i循环总个数-1次,最后一个是不需要比较的 for (i = 0; i < 3-1; i++) { for (int j = i + 1; j < 3; j++) { if (strcmp(p[i], p[j]) > 0) { char *tmp = p[i]; p[i] = p[j]; p[j] = tmp; } } } printf("%s %s %s\n", p[0], p[1], p[2]); // system("pause"); return 0; }
3、输入10个整数,将其中最小的数与第一个数对换,把最大的数与最后一个数对换。
写3个函数:
① 输人10个数;
② 进行处理;
③ 输出10个数。
这里我做成了排序哈哈哈
#include <stdio.h> void enter(int *p) { int i; int *pt1=p; // pt1用来存放数组首元素地址 for(i=0;p<(pt1+10);p++,i++) // pt1+10是控制长度 { scanf("%d",p); } } void print(int *p) { int i; int *pt1=p; for(i=0;p<(pt1+10);p++,i++) { printf("%d\t",*p); } } void sort(int *p) // 这里用选择排序法 { int i,j,tmp; for(i=0;i<9;i++) { for(j=i+1;j<10;j++) // i最大是8,所以j最大是9,条件如果改为9,比较少了一次咯 { if(*(p+i)>*(p+j)) { tmp=*(p+i); *(p+i)=*(p+j); *(p+j)=tmp; } } } } int main() { int array[10]; int *p; p=array; enter(p); sort(p); print(p); return 0; }
#include <stdio.h> #include <stdlib.h> void input(int *arry, int len) { for (int i = 0; i < len; i++) { scanf("%d", &arry[i]); } } void print(int *arry, int len) { for (int i = 0; i < len; i++) { printf("%d ", arry[i]); } printf("\n"); } void handle(int *arry, int len) { int max_num = arry[0], min_num = arry[0]; int *p_max = NULL, *p_min = NULL; // 设置最小值和最大值的指针变量 for (int i = 1; i < len; i++) { if (min_num > arry[i]) // 逐个比对后找出最小值 { min_num = arry[i]; p_min = &arry[i]; // 逐个比对后找到最小值的空间地址 } if (max_num < arry[i]) // 逐个比对后找出最大值 { max_num = arry[i]; p_max = &arry[i]; // 逐个比对后找到最大值的空间地址 } } int tmp; tmp = *p_min; *p_min = arry[0]; arry[0] = tmp; //最小值与第一个数据交换 tmp = *p_max; *p_max = arry[len - 1]; arry[len - 1] = tmp; //最大值与最后一个数据交换 } int main() { int arry[10]; printf("Please enter ten nums:"); input(arry, 10); handle(arry, 10); print(arry, 10); system("pause"); return 0; }
4、有n个整数,使前面各数顺序向后移m个位置,最后m个数变成最前面m个数,见图8.28。 写一函数实现以上功能,在主函数中输人n个整数和输出调整后的n个数。

#include <stdio.h> #include <stdlib.h> void move(int *arry, int n, int m) { int end_idx = n - m; //找到倒数第m个数据的位置,也就是要移动到数组首部的数据的起始位置 for (int i = 0; i < m; i++) { int *p = arry + end_idx + i; //从倒数第m个数据的位置开始逐渐向后偏移直到数组尾部 int tmp = *p; //获取到这个位置的值,用于数组前边数据向后偏移1位之后,向数组第i位赋值 for (int j = end_idx + i; j > i; j--) { //从第i位开始逐个向后偏移一位 *p = *(p - 1); p--; } *(arry + i) = tmp; //数组的前第i个数字逐个替换为后边被覆盖的值 } } int main() { int number[32], n, m, i; printf("Please enter the number of numbers: "); scanf("%d", &n); //先确定要输入多少个数字 printf("Please enter %d numbers: ", n); for (i = 0; i < n; i++) { scanf("%d", &number[i]); //输入指定个数的数字 } printf("Number of positions to move: "); scanf("%d", &m); //确定要向后移动多少个位置 move(number, n, m); for (i = 0; i < n; i++) { printf("%d ", number[i]); } printf("\n"); system("pause"); return 0; }
5、有n个学生围成一圈,顺序排号。从第1个学生开始报数(从1到3报数),凡报到3的学生退出圈子,到最后只留下一名学生,问最后留下的是原来第几号学生。
#include<stdio.h> int main() { int count=0,i,n,no=0; int num[50]; int *p; scanf("%d",&n); for(i=0;i<n;i++) num[i]=i+1; p=num; while(no<n-1) { if(*p!=0) count++; if(count==3) { no++; printf("no%d:%d\n",no,*p); *p=0; count=0; } p++; if(p==num+n) p=num; } p=num; while(*p==0) p++; printf("last no is:%d\n",*p); return 0; }
6、编写一函数,求一个字符串的长度。在main函数中输入字符串,并输出其长度。
#include<stdio.h> int count(char *p1) { int len=0; while(*p1!='\0') { pt1++; len++; } return len; } int main() { char str[20]; char *p=str; gets(str); printf("length of string is: %d \n",count(p)); return 0; }
7、有一个字符串a,内容为"My name is Li jilin.",另有一字符串b,内容为" Mr.Zhang Haoling is very happy."。写一函数,将字符串b中从第5个到第17个字符(即"Zhang Haoling")复制到字符串b中,取代字符串a中第12个字符以后的字符(即"Li jilin.")。输出新的字符串a。
#include <stdio.h> void compare(char *pt1,char *pt2) { char *a=pt1,*b=pt2; // 记录指针变量初值 while(pt1<a+11) // 指针指到第12个元素 { pt1++; } while(pt2<b+3) // 指针指到第4个元素 { pt2++; // 当前为4 } while(pt2<b+16) // 结束条件是指到第17个元素 { *pt1++=*pt2++; // a的第12个元素之后开始用b中5-17代替 } *pt1 = '\0'; } int main(){ char a[1024]="My name is Li jilin.", b[1024]="Mr.Zhang Haoling is very happy."; compare(a,b); puts(a); return 0; }
8、输入一行文字,找出其中大写字母、小写字母、空格、数字以及其他字符各有多少。
#include<stdio.h> void statistic(char *pt1) { int A=0,a=0,n=0,s=0,o=0; while(*pt1!='\0') { if(*pt1>=65 && *pt1<=90) { A++; }else if(*pt1>=97 && *pt1<=122) { a++; }else if(*pt1>=48 && *pt1<=57) { n++; }else if(*pt1==32) { s++; } else { o++; } pt1++; } printf("大写字符:%d\n小写字符:%d\n数字字符:%d\n空格字符:%d\n其他字符:%d\n",A,a,n,s,o); } int main() { char string[1024],*p=string; gets(string); statistic(p); return 0; }
9、在主函数中输入10个等长的字符串。用另一函数对它们排序。然后在主函数输出这10个已排好序的字符串。
#include<stdio.h> #include<string.h> void sort(char s[10][32]) { int i, j; for (i = 0; i < 10; i++) { for (j = i; j < 10; j++) { if (strcmp(s[i],s[j])) { char tmp[32]; strcpy(tmp,s[i]); strcpy(s[i],s[j]); strcpy(s[j],tmp); } } } } int main() { int i; char str[10][32]; printf("Please enter ten strings:\n"); for (i=0; i < 10; i++) { scanf("%s", str[i], 32); } sort(str); printf("\n"); for (i=0; i < 10; i++) { printf("%s\n", str[i]); } return 0; }
10、11、将n个数按输入时顺序的逆序排列,用函数实现。
1)直接逆序存放:
#include <stdio.h> void reverse(int *p,int len) { for(len;len>0;len--) scanf("%d",p+(len-1)); // 直接逆序存放 } void print(int *q,int len) { for(int i=0;i<len;i++) printf("%d\t",*(q+i)); printf("\n"); } int main() { int a[10]; int len=sizeof(a)/4,i; reverse(a,len); printf("\n"); print(a,len); /*for(len;len>0;len--) { printf("%d\t",a[10-len]); }*/ return 0; }
2)顺序存放,逆序读出:
#include<stdio.h> void reorder(int *arry, int n) { int *start = arry; int *end = arry + n - 1; for (; start < end; start++, end--) { int tmp = *start; *start = *end; *end = tmp; } return; } int main() { int arry[10]; printf("Please enter ten numbers:\n"); for (int i=0;i<10;i++) { scanf("%d", &arry[i]); } reorder(arry,10); printf("\n"); for(i=0;i<10;i++) { printf("%d ",arry[i]); } printf("\n"); //system("pause"); return 0; }
12、输人一个字符串,内有数字和非数字字符,例如:
a123x456 17960? 302tab5876
将其中连续的数字作为 一个整数,依次存放到一数组a中。例如,123放在a[0],456放在a[1]......共有多少个整数,并输出这些数。
#include <stdio.h> #include <string.h> void main() { char c[100],*p=c; int a[50],*q=a,num=0,i; gets(c); for(; *p!='\0'; p++) if(*p>='0' && *p<='9') { *q=(*p)-'0'; p++; while(*p>='0' && *p<='9') *q=(*q)*10+(*(p++)-'0'); num+=1; q+=1; } for(i=0,q=a; i<num; i++,q++) printf("%d ",*q); putchar('\n'); printf("一共输入了%d个数字。\n",num); }
13、编写一个函数,将一个3×3的整型二维数组转置,即行列转换。
#include<stdio.h> int main(){ void exchange(int *p); int a[3][3],i,j; int *p; printf("请输入二维数组:"); //二维数组的输入 for(i=0;i<3;i++){ for(j=0;j<3;j++){ scanf("%d",&a[i][j]); } } p=&a[0][0]; // 指向第一行 exchange(p); // 行列互换 printf("该二维数组转置为:"); //输出 for(i=0;i<3;i++){ for(j=0;j<3;j++){ printf("%d ",a[i][j]); } printf("\n"); } return 0; } void exchange(int *p){ int temp,i,j; for(i=0;i<3;i++){ for(j=i+1;j<3;j++){ temp=*(p+3*i+j); // 下标需要数组或指针类型 *(p+3*i+j)=*(p+3*j+i); // 数组元素是按行排列的,因此a[i][j]在a数组中是第(3*i+j)个元素 *(p+3*j+i)=temp; } } }

浙公网安备 33010602011771号