C語言程序設計第四版 譚浩強 第八章 課後答案(含註解)

第8章 善於利用指針


注:本章習題要求用指針的方法處理

1.輸入3個整數,按由小到大的順序輸出

#include<stdio.h>

void swap(int *a,int *b){
	int temp = *a;
	*a = *b;
	*b = temp;

}

int main(){
	int a,b,c;
	scanf("%d%d%d",&a,&b,&c);
	if(a>b) swap(&a,&b);
	if(a>c) swap(&a,&c); //第一個數a爲最小的數 
	if(b>c) swap(&b,&c); //再找出第二小的數 
	printf("%d%d%d",a,b,c);
} 

2.輸入3個字符串,按由小到大的順序輸出

#include<stdio.h>
#include<string.h>

void swap(char* p1,char* p2){
	char p[20];
	strcpy(p,p1);
	strcpy(p1,p2);
	strcpy(p2,p);
}

int main(){
	char str1[20],str2[20],str3[20];
	printf("input three line:\n");
	gets(str1);
	gets(str2);
	gets(str3);
	if(strcmp(str1,str2)>0) swap(str1,str2);
	if(strcmp(str1,str3)>0) swap(str1,str3);
	if(strcmp(str2,str3)>0) swap(str2,str3);
	printf("now,this order is:\n");
	printf("%s\n%s\n%s\n",str1,str2,str3); 
	
}

3.輸入10個整數,將其中最小的數與第1個數對換,把最大的數與最後一個數對換。寫3個函數①輸入10個數;②進行處理;③輸出10個數

#include<stdio.h>

void max_min_value(int* a){
	int *min,*max,*p,temp;
	max = min = a;
	for(p = a;p < a+10;p++)
		if(*p > *max) max = p;//找最大
	temp = a[9];a[9] = *max;*max = temp;
	for(p = a;p < a+10;p++)
		if(*p < *min) min = p;//找最小
	temp = a[0];a[0] = *min;*min = temp;	
	
}

int main(){
	int a[10] = {32,24,56,78,1,98,36,44,29,6};
	max_min_value(a);
	for(int i = 0 ;i < 10;i++){
		printf("%-3d",a[i]);
	}
	
}

4.有n個整數,使前面的各數向後移m個位置,最後m個數變成最前面m個數。

1 2 3 4 5 移動2位
4 5 1 2 3

#include<stdio.h>

//法1:借用指針+遞歸 
void move1(int a[],int n,int m){
	int *p,a_end;
	a_end = *(a+n-1); //保存最後一個元素的值
	for(p = a+n-1;p > a;p--)
		*p = *(p-1); //整個數組向後移動一位
	*p = a_end; //給第一個元素賦值爲變化前最後一個元素
	m--; //一趟向後移動一位 m-1
	if(m > 0) move1(a,n,m); //遞歸調用
}
//法二:利用新數組
void move2(int a[],int n,int m){
	int b[5],*p;
	for(int i = 0;i < 5;i++){
		b[ (i+m)%n ] = a[i]; //求模賦值
	}

	for(int i = 0;i < 5;i++){
		*(a+i) = *(b+i);
	//	printf("%-3d",a[i]);
	} 
	
} 


int main(){
	int a[5] = {1,2,3,4,5};
//	move1(a,5,2);
//	for(int i = 0;i < 5;i++)
//		printf("%-3d",a[i]);
	
	move2(a,5,2);
	for(int i = 0;i < 5;i++)
		printf("%-3d",a[i]);
}

5.n個人圍成一圈,順序排號。從第1個人開始報數(從1到3報數),凡報到3的人退出圈子,問最後留下的是原來的第幾號。

#include<stdio.h>

int main(){
	int num[50],k,i,n,m,*p;
	printf("請輸總共有多少人:\n");
	scanf("%d",&n);
	p = num;
	for(i = 0;i < n;i++)
	 *(p+i) = i+1; //1到n編號
	i = 0; //i爲每次循環時計數變量
	k = 0; //k爲按1,2,3報數時的計數變量 
	m = 0; //m爲退出人數 
	while(m < n-1){ //當退出人數比n-1少時(既未退出人數大於1時)執行循環體
		if( *(p+i) != 0 )  k++;
		if(k == 3){
			*(p+i) = 0; //退出的人編號置爲0
			printf("%d號淘汰\n",i+1);
			k = 0;
			m++;  //淘汰人數加1 
		}
		i++;
		if(i == n) i=0; //報數到尾後,i回覆爲0 
	} 
	while(*p == 0) p++;
	printf("最後剩下的元素爲: %d\n",*p);
	return 0; 
	 
} 

6.寫一個函數,求一個字符串的長度。在main函數中輸入字符串,並輸出其長度。

#include<stdio.h>

int strlen(char *s){//求字符串長度
	printf("strlen\n");
	int len = 0;
	char *p = s;
	while(*p != '\0'){ //報錯 p != '\0' 
		p++;
		len++;
	}
	return len;
}

int main(){
	char s[20];
	gets(s); //輸入字符串 
	//puts(s); 
	int len = strlen(s);
	printf("s的長度爲:%d\n",len);
}

7.有一個字符串包含n個字符。寫一個函數,將此字符串從第m個字符開始的全部字符串複製爲另一個字符串。

#include<stdio.h>
#include<string.h>

void copystr(char* p1,char* p2,int m);

int main(){
	char str1[20],str2[20];
	int m;
	printf("請輸入要複製字符串:\n");
	gets(str1);
	printf("請輸入從第幾位開始複製\n");
	scanf("%d",&m);
	if(strlen(str1) < m)
		printf("輸入有誤\n");
	else{
		copystr(str1,str2,m); 
		printf("複製後的字符串爲:\n"); 
		printf("%s",str2
		);	
	}
} 

void copystr(char* p1,char* p2,int m){
	printf("copystr~~~\n"); 
	int n=0;
	while(n < m-1){
		n++;
		p1++;
	}
	while(*p1 != '\0'){
		*p2 = *p1;
		p1++;
		p2++;
	}
	*p2 = '\0';
}

8.輸入一行文字,找出其中大寫字母、小寫字母、空格、數字以及其他字符各有多少。

#include<stdio.h>

int main(){
	int upper=0,lower=0,digit=0,space=0,other=0,i=0;
	char *p,s[20];
	printf("input string: ");
	while( ( s[i]=getchar() )!='\n') i++;
	p = s;
	while(*p != '\n'){
		if( (*p >= 'A')&&(*p <= 'Z') )
			++upper;
		else if((*p >= 'a')&&(*p <= 'z'))
			++lower;
		else if(*p == ' ')
			++space;
		else if((*p >='0' )&&(*p <='9'))
			++digit;
		else
			other++;
		p++;
	} 
	
	printf("upper case:%d   lower case:%d",upper,lower);
	printf("    space case:%d   digit case :%d   other case:%d\n",space,digit,other);
	
}

9.寫一個函數將一個3*3的矩陣轉置

#include<stdio.h>

//a[i][j]的地址是p+3*i+j
//a[j][i]的地址是p+3*j+i 
//a[i][j] a[j][i]地址相同 

void move(int *p){
	int i,j,t;
	for(i = 0;i < 3;i++){
		for(j = i;j < 3;j++){ //j=i 不是 j=0 
			t = *(p+3*i+j);
			*(p+3*i+j) = *(p+3*j+i);
			*(p+3*j+i) = t;
		}
	}
}

void move2(int a[][3]){
	int i,j,t;
	for(i = 0;i < 3;i++){
		for(j = i;j < 3;j++){ //j=i 不是 j=0 
			t = a[i][j];
			a[i][j] = a[j][i];
			a[j][i] = t;
		}
	}
}

int main(){
	int i,j,*p;
	int a[3][3]={1,2,3,4,5,6,7,8,9};
	p = &a[0][0];
	for(i = 0;i < 3;i++){
		printf("%d %d %d\n",a[i][0],a[i][1],a[i][2]);
	} 

	//move(p);
	move2(a);
	printf("變化後\n"); 
	for(i = 0;i < 3;i++){
		printf("%d %d %d\n",a[i][0],a[i][1],a[i][2]);
	} 
}

10.將一個5*5的矩陣中最大的元素放在中心,4個角分別放4個最小的元素(順序爲從左到右,從上到下),寫一個函數實現。套娃題,腦殼疼

#include<stdio.h>

void change(int *p){
	int i,j,temp;
	int *max,*min;
	max = min = p;
	for(i = 0;i < 5;i++){
		for(j = 0;j < 5;j++){
			if(*max < *(p+5*i+j)) max = p+5*i+j;
			if(*min > *(p+5*i+j)) min = p+5*i+j;
		}
	}
	temp = *(p+12); //將最大值與中間元素互換
	*(p+12) = *max;
	*max = temp;
	
	temp = *p; //將最小值與左上角元素互換
	*p = *min;
	*min = temp;
	
	min = p+1; //將a[0][1]的最地址給min,從該位置開始找最小的值
	for(i = 0;i < 5;i++){
		for(j = 0;j < 5;j++){
			if(i == 0 && j == 0) continue; 
			if(*min > *(p+5*i+j)) min = p+5*i+j;
		}
	}
	
	temp = *min;  //將第二小的值跟右上角的互換 
	*min = *(p+4);
	*(p+4) = temp;
	 
	min = p + 1; //找到第三小的值 
	for(i = 0;i < 5;i++){
		for(j = 0;j < 5;j++){
			if((i==0 && j==0)||(i==0 && j==4)) continue; 
			if(*min > *(p+5*i+j)) min = p+5*i+j;
		}
	}
	
	temp = *min;  //將第三小的值跟左下角的互換 
	*min = *(p+20);
	*(p+20) = temp;
	
	min = p + 1; //找到第四小的值 
	for(i = 0;i < 5;i++){
		for(j = 0;j < 5;j++){
			if((i==0&&j==0)||(i==0&&j==4)||(i==4&&j==0)) continue; 
			if(*min > *(p+5*i+j)) min = p+5*i+j;
		}
	}
	temp = *min;  //將第四小的值跟右下角的互換 
	*min = *(p+24);
	*(p+24) = temp;
}

int main(){
	int a[5][5]={1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16,17,18,19,20,21,22,23,24,25};
	int i,j,*p;
	p = &a[0][0];
	change(p);
	//打印變化後的數組 
	for(i = 0;i < 5;i++){
		for(j = 0;j < 5;j++)
			printf("%-4d",a[i][j]);
		printf("\n"); 
	}
} 

11.在主函數中輸入10個等長的字符串。用另一函數對他們排序。然後在主函數輸出這10個已經排好序的字符串

#include<stdio.h>
#include<string.h>

void sort(char s[3][6]){ //形參s是指向6個元素一組的指針 
	int i,j;
	char *p,temp[10]; //temp爲臨時容器長度要大於6 
	p = temp;
	//字符串版的冒泡排序   由於下面if是s[j]與s[j+1]比較所有i不能到3否則數組會溢出 
	for(i = 0;i < 2;i++){
		for(j = 0;j < 2-i;j++){
			if(strcmp(s[j],s[j+1])>0){
	//以下三行是將s[j]指向的一維數組與s[j+1]指向的一維數組的內容互換 
				strcpy(p,s[j]);
				strcpy(s[j],s[j+1]);
				strcpy(s[j+1],p);
			}
		}
	} 
} 

int main(){
	int i;
	char str[3][6]; //主要是算法數組大小無所謂
	printf("輸入3個長度爲6的字符串\n");
	for(i = 0;i < 3;i++)
		scanf("%s",str[i]);
	sort(str);
	printf("排序後爲:\n");
	for(i = 0;i < 3;i++)
		printf("%s\n",str[i]);
	return 0;
}

12.用指針數組處理上一題目,字符串不等長。

#include<stdio.h>
#include<string.h>

void sort(char *s[]){  
	int i,j;
	char *temp; //temp爲臨時容器長度要大於6 
	//字符串版的冒泡排序  
	for(i = 0;i < 4;i++){
		for(j = 0;j < 4-i;j++){
			if(strcmp(*(s+j),*(s+j+1))>0){
				temp = *(s+j);
				*(s+j) = *(s+j+1);
				*(s+j+1) = temp;
			}
		}
	} 
} 

int main(){
	int i;
	char *p[5],str[5][20]; //主要是算法,數組大小無所謂
	for(i = 0;i < 5;i++)
		p[i]=str[i];        //將第i個字符的首地址賦予指針數組p的第i個元素 
	printf("輸入5個字符串\n");
	for(i = 0;i < 5;i++)
		scanf("%s",p[i]);
	//sort(p);
	printf("排序後爲:\n");
	for(i = 0;i < 5;i++)
		printf("%s\n",p[i]);
	return 0;
}

13.寫一個函數用矩形求定積分的通用函數,分別別F(0,1) sinx dx,F(-1,1) cosx dx,F(0,2) exp(x) dx的定積分.

說明:sin,cos,exp已在系統的數學函數庫中.
#include<stdio.h>
#include<math.h>
int main()
{float integral(float(*)(float),float,float,int);//對integarl函數的聲明
float fsin(float);          //對fsin函數的聲明
float fcos(float);          //對fcos函數的聲明
float fexp(float);          //對fexp函數的聲明
float a1,b1,a2,b2,a3,b3,c,(*p)(float);
int n=20;
printf("input a1,b1:");
scanf("%f,%f",&a1,&b1);
printf("input a2,b2:");
scanf("%f,%f",&a2,&b2);
printf("input a3,b3:");
scanf("%f,%f",&a3,&b3);
p=fsin;
c=integral(p,a1,b1,n);
printf("The integral of sin(x) is:%f\n",c);
p=fcos;
c=integral(p,a2,b2,n);
printf("The integral of cos(x) is:%f\n",c);
p=fexp;
c=integral(p,a3,b3,n);
printf("The integral of exp(x) is:%f\n",c);
return 0;
}

float integral(float(*p)(float),float a,float b,int n)
{int i;
 float x,h,s;
 h=(b-a)/n;
 x=a;
 s=0;
 for(i=1;i<=n;i++)
  {x=x+h;
   s=s+(*p)(x)*h;
  }
  return(s);
}
  float fsin(float x)
    {return sin(x);}
  float fcos(float x)
    {return cos(x);}
  float fexp(float x)
    {return exp(x);}

14.將n個數按輸入時的順序逆序排列,用函數實現.

#include<stdio.h>

void sort(char* p,int m){
	int i;
	char temp,*p1,*p2; //雙指針,一頭一尾同時工作,替換值
	for(i=0;i<m/2;i++){ //i只到m的中間 
		p1 = p+i;//從頭到中間 
		p2 = p+(m-1-i);//從尾到中間 
		temp = *p1; //首尾交換 
		*p1 = *p2;
		*p2 = temp; 
	
	} 
} 

int main(){
	int i,n;
	char *p,num[20];
	printf("input n:");
	scanf("%d",&n);
	printf("input this numbers:\n");
	for(i=0;i<n;i++){  //i要從0開始 
		scanf("%d",&num[i]);
	}
	p = &num[0];
	sort(p,n);
	for(i=0;i<n;i++){
		printf("%d ",num[i]);
	}
} 

15.有一個班4個學生,5門課程.①求第一門課程的平均分;②找出有兩門以上課程不及格的學生,輸出他們的學號和全部課程及平均成績;③找出平均成績在90分以上或者全部課程在85分以上的學生.分別編三個函數實現3個要求

#include <stdio.h>
/*
輸入課程 
English
computer
math
physics
chemistry
輸入成績 
101 34 56 88 99 89
102 27 88 99 67 78
103 99 90 87 86 89
104 78 89 99 56 77
*/ 
void avsco(float *,float *);   // 求每個學生的平均成績的函數
void avcour1(char (*)[10],float *); // 求第一課程的平均成績的函數
void fali2(char course[5][10],int num[],float *pscore,float aver[4]); // 找兩門以上課程不及格的學生的函數
void good(char course[5][10],int num[4],float *pscore,float aver[4]); //滿足③ 

int main()
{
 	int i,j,*pnum,num[4];
 	float score[4][5],aver[4],*pscore,*paver;
 	char course[5][10],(*pcourse)[10];
 	printf("input course:\n");
 	pcourse=course;   
 	for (i=0;i<5;i++)
 		scanf("%s",course[i]);
	 printf("input NO. and scores:\n");
	 printf("NO.");
	 for (i=0;i<5;i++)
	   printf(",%s",course[i]);
	 printf("\n");
	 pscore=&score[0][0];
	 pnum=&num[0];
	 for (i=0;i<4;i++)
	 {
	 	scanf("%d",pnum+i); //pnum記錄學號 num[i][0]  
	  	for (j=0;j<5;j++)
	   		scanf("%f",pscore+5*i+j); //pscore 記錄分數 
	 }
	 paver=&aver[0];
	 printf("\n\n");             
	 avsco(pscore,paver);                  // 求出每個學生的平均成績
	 avcour1(pcourse,pscore);                // 求出第一門課的平均成績 (pcourse指向課程數組) 
	 printf("\n\n");
	 fali2(pcourse,pnum,pscore,paver);       // 找出2門課不及格的學生
	 printf("\n\n");
	 good(pcourse,pnum,pscore,paver);        // 找出成績好的學生
	 return 0;
}

void avsco(float *pscore,float *paver)  // 求每個學生的平均成績的函數
{
	
 	int i,j;
 	float sum,average;
  	for (i=0;i<4;i++)
    {
	   	sum=0.0;
	    for (j=0;j<5;j++)
	     	 sum=sum+(*(pscore+5*i+j));       //累計每個學生的各科成績
	    average=sum/5;                   //計算平均成績
	    *(paver+i)=average;  //paver是存每個學生平均成績的數組 
    }
}

//char (*pcourse)[10]:是一個數組指針,這個指針是指向一個度大小爲10的字符數組; 
void avcour1(char (*pcourse)[10],float *pscore)      // 求第一課程的平均成績的函數
 {int i;
  float sum,average1;
  sum=0.0;
  for (i=0;i<4;i++)
    sum=sum+(*(pscore+5*i));               //累計每個學生的得分 sum最終爲第一列值的和 
  average1=sum/4;                        //計算平均成績
  printf("course 1:%s average score:%7.2f\n",*pcourse,average1);
}

void fali2(char course[5][10],int num[],float *pscore,float aver[4]) 
           // 找兩門以上課程不及格的學生的函數
 {
	 int i,j,k,labe1;
	  printf("        ==========Student who is fail in two courses=======  \n");
	  printf("NO. ");
	  for (i=0;i<5;i++)
	    printf("%11s",course[i]);
	  printf("    average\n");
	  for (i=0;i<4;i++)
 	  {
 	 	
	  	labe1=0;      //記錄不及格的科目數 
   		for (j=0;j<5;j++)
    		 if (*(pscore+5*i+j)<60.0) labe1++;
  		if (labe1>=2)
    	{
			printf("%d",num[i]);
   			for (k=0;k<5;k++)
      			printf("%11.2f",*(pscore+5*i+k)); //輸出有兩門不及格學號的所有成績 
    		 printf("%11.2f\n",aver[i]);  //直接輸出之前記錄下的平均值 
   		 }
      }
}

void good(char course[5][10],int num[4],float *pscore,float aver[4])
   // 找成績優秀學生(各門85以上或平均90分以上)的函數
 {
  int i,j,k,n;
  printf("         ======Students whose score is good======\n");
  printf("NO. ");
  for (i=0;i<5;i++)
    printf("%11s",course[i]);
  printf("    average\n");
  for (i=0;i<4;i++)
   {n=0;
    for (j=0;j<5;j++)
      if (*(pscore+5*i+j)>85.0) n++;
    if ((n==5)||(aver[i]>=90))
     {printf("%d",num[i]);
      for (k=0;k<5;k++)
        printf("%11.2f",*(pscore+5*i+k));
      printf("%11.2f\n",aver[i]);
     }
 }
}

16. 輸入一個字符串,內有數字和非數字字符,例如:

a123x456 17960? 302tab5876

將其中連續的數字作爲一個整數,依次存放到一數組a中。例如,123存入在a[0],456存放在a[1]……統計共有多少整數,並輸出這些數。

#include <stdio.h>
int main()
{
 char str[50],*pstr;
 int i,j,k,m,e10,digit,ndigit,a[10],*pa;
 printf("input a string:\n");
 gets(str);
 pstr=&str[0];    /*字符指針pstr置於數組str 首地址*/
 pa=&a[0];        /*指針pa置於a數組首地址*/
 ndigit=0;        /*ndigit代表有多少個整數*/
 i=0;             /*代表字符串中的第幾個字符*/
 j=0;            /*記錄數字連續的個數*/ 
 while(*(pstr+i)!='\0')
 {if((*(pstr+i)>='0') && (*(pstr+i)<='9'))
       j++;
     else
       {if (j>0)
        {digit=*(pstr+i-1)-48;          /*將個數位賦予digit,字符 0對應的ascii碼爲 48*/
         k=1;
         while (k<j)     /*將含有兩位以上數的其它位的數值累計於digit*/
           {e10=1;
         for (m=1;m<=k;m++)
         e10=e10*10;                  /*e10代表 該位數所應乘的因子*/
         digit=digit+(*(pstr+i-1-k)-48)*e10;  /*將該位數的數值\累加於digit*/
         k++;                   /*位數K自增*/
           }
         *pa=digit;               /*將數值賦予數組a*/
         ndigit++;
         pa++;                    /*指針pa指向a數組下一元素*/
         j=0;
        }
    }
     i++;
    }
 if (j>0)                         /*以數字結尾字符串 j還是>0不能處理,或者是全是數字的情況下 j也是 >0*/
  {digit=*(pstr+i-1)-48;          /*將個數位賦予digit*/
   k=1;
   while (k<j)          /* 將含有兩位以上數的其它位的數值累加於digit*/
    {e10=1;
     for (m=1;m<=k;m++)
       e10=e10*10;            /*e10代表位數所應乘的因子*/
     digit=digit+(*(pstr+i-1-k)-48)*e10;  /*將該位數的數值累加於digit*/
     k++;  /*位數K自增*/
    }
   *pa=digit;                 /*將數值賦予數組a*/
   ndigit++;
   j=0;
  }
  
  
  printf("There are %d numbers in this line, they are:\n",ndigit);
  j=0;
  pa=&a[0];
  for (j=0;j<ndigit;j++)            /*打印數據*/
    printf("%d ",*(pa+j));
  printf("\n");
  return 0;
}

17.編寫一個函數,實現兩個字符串的比較.即自己寫一個strcmp函數,函數原型爲strcmp(char *p1,char *p2);

#include<stdio.h>

int mystrcmp(char *p1,char *p2){
	int i = 0;
	while( *(p1+i) == *(p2+i) )
		if( *(p1+i++) == '\0' ) return 0;  //相等時返回結果0 
	return (*(p1+i) - *(p2+i));  //不等時返回第一個結果不相等字符的差值 
	
} 
int main(){
	int m;
	char str1[20],str2[20],*p1,*p2;
	printf("請輸入兩串字符串\n");
	gets(str1);
	gets(str2);
	p1 = str1;
	p2 = str2;
	m = mystrcmp(p1,p2);
	printf("%d",m);
}

18編寫一個程序,輸入月份號,輸出改月份的英文月名.例如輸入"3",則輸出"march",要求用指針數組處理.

#include <stdio.h>

/*
void someFunc(char *someStr);
再看這個函數調用:
someFunc("I'm a string!");
把這兩個東西組合起來,用最新的g++編譯一下就會得到標題中的警告。
爲什麼呢?原來char *背後的含義是:給我個字符串,我要修改它。
而理論上,我們傳給函數的字面常量是沒法被修改的。
所以說,比較和理的辦法是把參數類型修改爲const char *。
這個類型說背後的含義是:給我個字符串,我只要讀取它。
*/

int main()
{
    const char * month[13]={"illegal","January", "Februray", "March", "April", "May", "June", "July",
						"August", "September", "October", "November", "December"};
    int n;
    printf("Please enter month: \n");
    scanf("%d", &n);
    if ( (n <= 12) && (n >= 1) )
    	printf("It is %s.\n",*(month+n));
    else{
		printf("Error!\nPlease enter month: ");
		scanf("%d", &n);
		//output(m, month);
	}
    
    return 0;
}

19(1)編寫一個函數new,對n個字符開闢連續的存儲空間,此函數應返回一個指針地址,指向字符串開始的空間.new(n)表示分配了n個字節的內存空間

19(2)編寫函數free,free的作用是是newp的值恢復爲p.

new爲關鍵字自己寫函數不要用這個new命名

#include<stdio.h>

#define NEWSIZE 1000  //指定開闢存儲區的最大容量
int newbuf[NEWSIZE]; //定義字符串數組newbuf
int *newp = newbuf; //定義指針變量newp,指向存儲區的始 端


int* my_new(int n){ //定義開闢存儲區的函數new,開闢數組後返回指針 
	if(newp+n <= newbuf+1000){ //開闢區未超過newbuf數組的大小 
		newp += n;  //newp指向存儲區末尾 
		return newp-n; //返回首地址 
	}
	else
	return NULL; //存儲區不夠分配時,返回一個空指針 
} 

void my_free(int *p){  //釋放存區函數 
	if(p >= newbuf && p<newbuf+1000)
		newp = p;
}

int main(){

	int *p = my_new(5);

	for(int i=0;i<5;i++){
		p[i]=i;
	} 
	my_free(p); //讓newp回到初始位置 

	for(int i=0;i<5;i++){
		printf("%d\n",newp[i]);  //此時newp的位置等於 p[0] 
	} 
} 

20.用指向指針的指針的對5個字符串進行排序並輸出

/* 測試數據 
China
America
India
Philippines
Canada
排序後輸出爲:
America
Canada
China
India
Philippines

AZZ
B
C
D
E
*/

#define _CRT_SECURE_NO_WARNINGS 1
#include<stdio.h>
#include<stdlib.h>
#include<string.h>
void sort(char **p) //冒泡排序交換字符串 
{
	char **q, **s, *t;
	for (q = p; q < p + 4; q++) 
	{
		for (s = p+4; s > q; s--)
		{
			if (strcmp(*q, *s) > 0)
			{
				printf("*q_初始地址=%d\n",*q);
				printf("*s_初始地址=%d\n",*s);
				printf("\n");
				
				printf("*q_字符串=%s\n",*q);
				printf("*s_字符串=%s\n",*s);
				printf("\n");
				t = *q;
				*q = *s;
				*s = t;
				printf("*q_排序後地址=%d\n",*q);
				printf("*s_排序後=%d\n",*s);
				printf("\n");
				
				printf("*q_排序後值=%s\n",*q);
				printf("*s_排序後值=%s\n",*s);
				printf("\n");
			}
		}
		for (int i = 0; i < 5; i++)
		{
			printf("*p[%d]=%s\n",i, *(p+i) );
		}
		printf("\n");
	}
}
int main()
{
	char *a[5],  **p;
	char b[5][100];
	int i;
	for (i = 0; i < 5; i++)
		a[i] = b[i];   //將第i個字符串的首地址賦值予指針數組a的第i個元素 
	printf("請依次輸入五個字符串:\n");
	for (i = 0; i < 5; i++)
		scanf("%s", a[i]);
	p = a;
	sort(p);
	printf("排序後輸出爲:\n");
	for (i = 0; i < 5; i++)
	{
		printf("%s\n", a[i]);
	}
	system("pause");
	return 0;

}

21.用指向指針的指針方法對輸入的n個整數排序並輸出.

#include<stdio.h>

void sort(int **p,int n){
	int i,j,*temp;
	for(i = 0;i < n-1;i++)
		for(j = n-1;j > i;j--){
			if( **(p+j-1) > **(p+j) ){ //*p表示數組的地址,* *p表示取數組地址的值.
				temp = *(p+j-1);
				*(p+j-1) = *(p+j);
				*(p+j) = temp;
			}
		}
} 

int main(){
	int i,n,*pstr[20],**p;
	int a[20]={34,98,56,12,22,65,1};//n=7
	printf("請輸入n:\n");
	scanf("%d",&n);
	printf("排序前:\n"); 
	for(i = 0;i < n;i++){
		pstr[i] = &a[i];
		printf("%d ",a[i]);
	}
	p = pstr;
	sort(p,n); //改變的是指針數組*pstr[]裏面存放 a[]數組的地址 的順序 
	printf("\n排序後:\n"); 
	for(i = 0;i < n;i++)
		printf("%d ",*pstr[i]); 
	//printf("%d ",a[i]); 	//a[i]數組的值位置沒有發生變化 
	
} 
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章