{if(i%3==0&&i%7==0)
s=s+i; }
s=sqrt(s);
return(s); }
/********** 【习题7.184】编写函数,根据公式s=1+1/(1+2)+1/(1+2+3)+ „„1/(1+2+3+„+n)计算s,并作函数值返回。例如:若n的值 为11时,函数的值为1.833333。 **********/ float func(int n) { int i; float j=1.0,s=1.0; for(i=2;i<=n;i++) {j=j+i; s=s+1/j; } return (s); }
/********** 【习题7.187】编写函数,计算并输出下列级数和: 1/(1*2)+1/(2*3)+1/(3*4)+ „ +1/(n*(n+1)),
并返回结果。例如,当n=10时,函数值为0.90909。 **********/ float func(int n) { int i; float x,y; for(i=1;i<=n;i++) {x=i*(i+1); y=y+1/x; } return(y); }
/********** 【习题7.195】编写函数,求m!/(n!(m-n)!)的值,结果由函数值
返回。m与n为两个正整数且要求m>n。例如:m=12,n=8时,运行 结果为495.000000。 **********/ float func(int m, int n) { int i,j,k,l; float x=1.0,y=1.0,z=1.0; if(m<=n) l=m,m=n,n=l; for(i=1;i<=m;i++) x=x*i; for(j=1;j<=n;j++) y=y*j; for(k=1;k<=m-n;k++) z=z*k ; z=x/(z*y); return(z);
}
/********** 【习题7.205】编写函数,计算并返回给定整数n除了1与自身 之外的所有因子之和。例如,若n=8,则函数返回6(=2+4)。 **********/ int func(int n) { int i,j,k; for(i=1;i<=0.5*n;i++)
for(j=1;j<=n;j++)
if(i*j==n)
k=k+i+j;
k=k-1-n;
k=k/2;
return(k);
}
/********** 【习题7.255】编写函数,根据以下公式返回π的值
π/2 = 1+1!/3+2!/(3*5)+...+n!/(3*5*7*...*(2*n+1)) 要求满足精度eps,即一旦有小于eps的项值加入后停止迭代。 例如,若精度eps=0.0005,则返回值为3.141106。 **********/ float func(float eps) { int i; float x=1,y=1,z; for(i=1;(x/y)>=eps;i++) {x=x*i; y=y*(2*i+1); z=z+x/y;} z=2*z+2; return(z);
}
/********** 【习题7.265】编写函数,将数组s所存字符串中下标和ASCII码 均为偶数的字符,依次存入数组t中,并构成一个新串。例如, 若s中的字符串值为ABCD123456,则t中的串值应为246。 **********/ void func(char s[], char t[]) { int i,j,m=0; for(i=0;s[i]!=0;i++)
if((i%2==0)&&(s[i]%2==0)) t[j]=s[i],j++;
}
/********** 【习题7.275】假定字符串s中可能含有字符'*'。请编写函数, 若字符串s的尾部连续的'*'多于n个,则删除多余的'*'。例如, 若s="*****A*BCDE**F*******"且n=4,则调用函数后,字符串 s="****A*BCDE**F****";若n≥7,则字符串s中的内容不变。 注意:函数中不得调用C语言提供的字符串函数。 **********/ void func(char s[], int n) { int i,j,k,d=0,c=0,t=0; while(s[d++]) c++; for(i=c-1;i>=0;i--)
{if(s[i]=='*')
t++;
else break;}
if(t>n)
{k=t-n;
s[c-k]='\0';}
}
/********** 【习题7.315】编写函数,求出1到n之间(含n)能被7或11整除的 所有整数并依次存入数组a中,函数值为这些数的个数。例如, 若n=15,则依次存入数组a中的数为
7、11和14,函数值为3。 **********/ int func(int n, int a[]) { int i,j=0; for(i=1;i<=n;i++) if((i%7==0)||(i%11==0)) a[j]=i,j++; return(j); }
/********** 【习题7.317】编写函数,求出1到n之间(含n)都能被c和d整除 的所有整数并依次存入数组a中,函数值为这些数的个数。例如, 若n=20,c=2,d=3,则依次存入数组a中的数为
6、12和18,函 数值为3。 **********/ int func(int n, int c, int d, int a[]) {
int i,j;
for(i=1;i<=n;i++)
if((i%c==0)&&(i%d==0))
a[j]=i,j++;
return(j); }
/********** 【习题7.325】假设数组a存放了n个人的年龄。编写函数,用 数组c统计各年龄段的人数,其中c[0]为0至9岁年龄段的人数, c[1]为10至19岁年龄段的人数,c[2]为20至29岁年龄段的人 数,其余依此类推,c[10]为100岁(含100)以上年龄的人数。 **********/ void func(int n, int a[], int c[]) {
int i,b; for(i=0;i<=10;i++) c[i]=0;
for(i=0;i=100) c[10]++; else { b=a[i]/10; c[b]++; }} }
/********** 【习题7.335】假设字符数组a中存放了按由小到大连续存放的 字符构成的字符串(后跟一个'\0'作为结束符)。编写函数, 删去字符串中所有重复的字符(各自只保留一个),并使得保 留的字符仍构成一个字符串(连续存放,'\0'作为结束符)。
函数返回a中保留的字符串长度。例如,若a中的字符串值为:
AAABBCDFFFHHHKLMMM 则删除重复字符之后,函数返回值为9,a中的字符串值为:
ABCDFHKLM **********/ int func(char a[]) { int i; //while(a[i]!='\0') //i++; char c[26];int j=1,k; c[0]=a[0]; for(i=1;a[i]!='\0';i++) if(a[i]!=a[i-1]) c[j]=a[i],j++; while(c[k]!='\0') k++; for(i=0;i<=k;i++) a[i]=c[i]; return(k);
}
/********** 【习题7.345】假设字符数组s中存放了一行字符串,含有由小写 字母组成的若干单词,单词之间由若干个空格隔开(串的开头没 有空格)。编写函数,统计一行字符串中单词的个数,并作为函 数值返回。 **********/ int func(char s[]) { int i,j; for(i=0;s[i]!=0;i++) if(s[i]==' ') j++; j+=1; for(i=0;s[i]!=0;i++) if((s[i]==' ')&&(s[i+1]==' ') ) j--; return(j); }
/********** 【习题7.355】假定字符串s中可能含有字符'*'。请编写函数, 将字符串s中前导'*'全部移到字符串的尾部。例如,若s的串
值为***A*BC*DEF*G**,移动后,串值应为A*BC*DEF*G*****。 注意:不得调用C语言提供的字符串函数。 **********/ void func(char s[]) { int i,j=0,k=0; char b[100];
for(i=0;s[i]!='\0';i++)
{
if(s[i]=='*')
k++;
else break;
} for(i=k;s[i]!='\0';i++)
{
b[j]=s[i];
j++;
} for(i=0;i{
if(is[i]=b[i];
else s[i]='*';
}
s[i]='\0';
}
/********** 【习题7.513】编写函数,计算并返回数组a中头n个 元素的乘积。
**********/ long func(int a[], int n) {
int i,s=1;
for(i=0;is=s*a[i];
return(s); }
/********** 【习题7.523】编写函数,计算并返回数组a中头n个 元素的平方和。
**********/ long func(int a[], int n) {
int i,s;
for(i=0;is=s+a[i]*a[i];
return (s); }
/********** 【习题7.533】假设某班选举班长,k位候选人的 号码分别为1至k,n张选票已存入数组v(每个元 素值在1至k之间)。编写函数,用数组c统计各位 候选人的得票(c[i]为i号候选人的得票数)。
**********/ void func(int v[], int n, int k, int c[]) { int i,j; for(j=0;j<=k;j++) c[j]=0; for(i=0;i/********** 【习题7.535】假设某班选举班长,k位候选人的 号码分别为1至k,n张选票已存入数组v(每个元 素值在1至k之间)。编写函数,用数组c统计各位 候选人的得票(c[i]为i号候选人的得票数),并 返回得票最高的人的号码。
**********/ int func(int v[], int n, int k, int c[]) {
int i,j,max; for(i=0;i<5;i++)
c[i]=0; for(i=0;ic[v[i]]++;
max=c[0]; for(i=1;i<=k;i++)
if(max{
j=i;
max=c[i];
}
return j;
}
/********** 【习题7.563】编写函数,把长整数n的各位数字从低 位到高位依次存储在数组d中,并返回n的位数。例如, 若n=2579,则n的位数为4,d[0..3]=9,7,5,2。 **********/ int func(long n, int d[]) {int i; while(n>0) {d[i]=n%10,i++; n=n/10; } return(i); }
/********** 【习题7.565】编写函数,把长整数n的各位数字从高 位到低位依次存储在数组d中,并返回n的位数。例如, 若n=2579,则n的位数为4,d[0..3]=2,5,7,9。 **********/ int func(long n, int d[]) { int i,j; int a[25]; for(i=0;n!=0;i++)
{
a[i]=n%10;
n=n/10;
}
j=i;
for(i=0;id[i]=a[j-i-1];
return j; }
/********** 【习题7.655】编写函数,用数组num统计字符串s中各元音字母 (即:A、E、I、O、U)的个数。注意:不分大、小写。例如, 若s="THIs is a book",则num[0..4]={1,0,2,2,0}。 **********/ void func(char *s, int *num) /* 功能:用数组num统计符串s中元音字母出现的个数 */ {
int i;num[0]=0, num[1]=0,num[2]=0,num[3]=0,num[4]=0;
for(i=0;s[i]!='\0';i++)
if((s[i]=='a')||(s[i]=='A'))
num[0]++;
for(i=0;s[i]!='\0';i++)
if((s[i]=='e')||(s[i]=='E'))
num[1]++;
for(i=0;s[i]!='\0';i++)
if((s[i]=='i')||(s[i]=='I'))
num[2]++;
for(i=0;s[i]!='\0';i++)
if((s[i]=='o')||(s[i]=='O'))
num[3]++;
for(i=0;s[i]!='\0';i++)
if((s[i]=='u')||(s[i]=='U'))
num[4]++;
}
/**【习题7.675】假设在数组s中存放了n位学生的成绩。 编写函数,用数组p统计各分数段的人数,其中p[0]为 不足60分的人数,p[1]为60至69分的人数,p[2]为70 至79分的人数,p[3]为80至89分的人数,p[4]为90至 100分的人数。 **********/ void func(int s[], int n, int p[]) {
int i;
for(i=0;i<5;i++)
p[i]=0;
for(i=0;i{if(s[i]<60)
p[0]++;
if((s[i]>=60)&&(s[i]<70))
p[1]++;
if((s[i]>=70)&&(s[i]<80) )
p[2]++;
if((s[i]>=80)&&(s[i]<90) )
p[3]++;
if((s[i]>=90)&&(s[i]<=100))
p[4]++;} }
/********** 【习题7.685】编写函数,从小到大依次求出能整除m的各整数, 并存放在数组d中,这些除数的个数由n返回。例如,若m=20,则 有6个数能整除它,依次是1,2,4,5,10,20。 **********/ void func(int m, int d[], int *n) { int i,j; for(i=1;i<=m;i++) if(m%i==0) d[j]=i, j++; *n=j; }
/********** 【习题7.755】通信时经常用到加密技术,把消息加密后再传输。 编写一个用于加密消息的函数,把字符串str中的小写字母改成
“(其ASCII码加上字符串key中每个字符ASCII码的平方)除以128 所得的余数”作为ASCII码对应的字符,其它的字符不变,其中 str称为消息原文,key称为密钥。 请思考:如何解密恢复原文,这种加密方法能准确地恢复原文吗? **********/ void func(char *str,char *key) /* 功能:用key作为密钥对字符串str进行加密处理 */ {
int i,j,k;
for(i=0;key[i]!='\0';i++)
k=k+key[i]*key[i];
for(j=0;str[j]!='\0';j++)
if((str[j]<='z')&&(str[j]>= 'a') )
str[j]=(str[j]+k)%128; }
int min(int x, int y, int z) /* 返回3个整数x,y和z中最小的数 */ {
if(x>y)
x=y;
if(x>z)
x=z;
return(x);
}
/********** 【习题8.011】请编写函数func(char s[], char t[], int n),
由数组s中长度为n的字符序列构造其逆序列,并存储在数组t中。 例如,由给定字符序列s="are"求得逆序列t="era";由s="time" 求得t="emit"。 **********/ void func(char s[], char t[], int n)
/* 数组s的前n个元素存放给定的字符序列,
数组t的前n个元素存放s的逆序列。
注意:数组的下标从0开始。 */ { int i; for(i=0;i}
/********** 【习题8.012】请编写函数func(char*s, char *t),由字符
串s构造其逆串t。例如,由给定串s="are"求得逆串t="era"; 由s="time"求得t="emit"。 **********/ void func(char *s, char *t)
/* s是给定字符串的起始地址,
t是求得s的逆串的起始地址 */ { int i,j; for(j=0;s[j]!='\0';j++) ; for(i=0;i/********** 【习题8.015】对长度为n的字符串s1,除首、尾字符外,将 其余字符按ASCII码降序排列,组合成一个新的字符串s2。 **********/ void func(char *s1, char *s2, int n) /* s1为字符串的起始地址,
s2为新字符串的起始地址,
n为字符串的长度。
要求:s1串不能发生改变,
s2串存放新的字符串。 */ { int i,j;
char t;
n=strlen(s1);
for(i=0;i*(s2+i)=*(s1+i);
for(j=1;jfor(i=1;i<=n-2-j;i++)
{ if(*(s2+i)
{ t=*(s2+i);
*(s2+i)=*(s2+i+1);
*(s2+i+1)=t;
} }}
/********** 【习题8.016】对字符串s1,除首、尾字符外,将其余字符 按ASCII码降序排列,组合成一个新的字符串s2。 **********/ void func(char *s1, char *s2) {int n; n=strlen(s1); int i,j,k; char t;
for(i=0;is2[i]=s1[i];
s2[i]='\0';
for(i=1;i{
k=i;
for(j=i+1;jif(s2[k]k=j;
t=s2[i];
s2[i]=s2[k];
s2[k]=t;
} }
/********** 【习题8.020】在字符串s中查找字符c,如果找到,返回字符c 首次出现在字符串s中的位置指针;否则,返回空指针NULL。 **********/ char *match(char *s, char c)
/* 返回字符在串s中首次出现的位置指针 */ {
int i;
for(i=0;s[i]!='\0';i++)
if(s[i]==c)
return(s+i);
return(NULL);
}
/* 8.030 先编写一个判断素数的函数。再编写一个函数将一个
偶数表示为两个素数之和,并返回其中较小的素数。
注:素数指只能被1和自身整除的正整数。规定0,1不是素数。
*/ int prime(int n)
/* 判断素数,如果是素数返回1,不是素数则返回0 */ { int t;
if(n==1)
return 0;
for(t=2;t<=(n/2);t++)
if(n%t==0)
return 0;
return 1; }
int f(int i)
/* 将偶数i表示为两个素数之和,返回其中较小的素数*/ {
int n; for(n=3;n<=i;n++) if(prime(i-n)&&prime(n)) return n; }
/********** 【习题8.033】编写函数,计算年份year中第yearday天相应的月 和日。例如,调用函数month_day(2000,61,&m,&d)之后,m=3, d=1,即2000年的第61天是3月1日。 **********/ int month_day(int year, int yearday, int *pmonth, int *pday) /* year是年,
yearday是天数,
若year和yearday合理,
则*pmonth和*pday是计算得出的月和日,函数返回1;
否则,函数返回0。 */ { int s[12]={31,28,31,30,31,30,31,31,30,31,30,31},m ;
if(year%4==0&&year%100!=0||year%400==0)
s[1]=29; if(year<1||yearday<1||(s[1]==28&&yearday>365)||(s[1]==29&&yearday>366))
return 0;
else
for(m=0;yearday-s[m]>0&&m<12;m++)
yearday-=s[m];
if(yearday==0)
{
m=m-1;
yearday=s[m];
}
*pmonth=m+1;
*pday=yearday;
return 1;
}
/********** 【习题8.044】请编写一个函数func,通过略去非数字字符,将字符串 s转换为一个整数(不得调用C语言提供的将字符串转换为整数的函数)。 **********/ long func(char *s)
/* s是一个数字字符串的地址,
函数返回值为由s含有的数字字符转换得到的数(包含正负数情况)
*/ { int i,j=1,k=0,flag=1; long n=0; for(i=0;s[i];i++) {
if(s[i]=='+'&&flag)
{
flag=0;
j=1;
}
if(s[i]=='-'&&flag)
{
flag=0;
j=-1;
}
if(s[i]>47&&s[i]<58)
{
n=n*10;
n=n+(s[i]-'0');
}
if(n) flag=0; } n=n*j; return n; }
/* 8.050 编写函数,将字符串中ASCII码最小的字符放在第一
个字符位置,其余字符依次往后移。
*/ void func(char *str) /* 将字符串str中ASCII码最小的字符放在第一个 */ /* 字符位置,其余字符依次往后移。
*/ { int i=1,m=0,k; for(m=0,i=1;str[i]!='\0';i++) { if(str[m]>str[i]) m=i; } k=str[m]; for(i=m-1;i>=0;i--) str[i+1]=str[i]; str[0]=k; }
/* 8.060 编写函数将一个nxn的二维数组按“次对角线”翻转。
例如:翻转前的数组
翻转后的数组
1 2 3
9 6 3
4 5 6 ---> 8 5 2
7 8 9
7 4 1 */ void invert(char a[N][N]) { int i,j; int b[N][N]; for(i=0;ifor(i=0;i/* 8.064 编写函数将一个NxN的二维数组“水平”翻转。
例如:翻转前的数组
翻转后的数组
1 2 3
7 8 9
4 5 6 ---> 4 5 6
7 8 9
1 2 3 */ void invertH(char a[N][N]) {
int i,j; int b[N][N]; for(i=0;i/* 8.065 编写函数将一个NxN的二维数组“垂直”翻转。
例如:翻转前的数组
翻转后的数组
1 2 3
3 2 1
4 5 6 ---> 6 5 4
7 8 9
9 8 7 */ void invertV(char a[N][N]) { int i,j; int b[N][N]; for(i=0;i/* 8.067 编写函数将一个NxN的二维数组的周边元素“顺时针”轮转1位。
例如:轮转前的数组
轮转后的数组
1 2 3
4 1 2
4 5 6 ---> 7 5 3
7 8 9
8 9 6 */ void turningClockwise(char a[N][N]) { int i,j,row=0,column=0; int tmp,t; int flag=1;
for(i=0;ifor(i=0;i/*8.068 编写函数将一个NxN的二维数组的周边元素“逆时针”轮转1位。
例如:轮转前的数组
轮转后的数组
1 2 3
2 3 6
4 5 6 ---> 1 5 9
7 8 9
4 7 8 */ void turningAnticlockwise(char a[N][N]) { int i;
char t=a[0][0];
for(i=0;ia[0][i]=a[0][i+1];
for(i=0;ia[i][2]=a[i+1][2];
for(i=0;ia[2][2-i]=a[2][2-i-1];
a[2][0]=a[1][0];
a[1][0]=t; }
/* 8.072 编写函数将一个NxN的二维数组a的元素按行向右轮转1位。
例如:轮转前的数组
轮转后的数组
1 2 3
3 1 2
4 5 6 ---> 6 4 5
7 8 9
9 7 8 */ void turningRight(char a[N][N]) { int b[N][N],i,j; for(i=0;ifor(i=0;i/* 8.075 编写函数将一个NxN的二维数组a的元素按行向左轮转1位。
例如:轮转前的数组
轮转后的数组
1 2 3
2 3 1
4 5 6 ---> 5 6 4
7 8 9
8 9 7 */ void turningLeft(char a[N][N]) {
int b[N][N],i,j; for(i=0;ifor(i=0;i/* 8.082 编写函数将一个NxN的二维数组a的元素按列向下轮转1位。
例如:轮转前的数组
轮转后的数组
1 2 3
7 8 9
4 5 6 ---> 1 2 3
7 8 9
4 5 6 */ void turningDown(char a[N][N]) { int b[N][N],i,j; for(i=1;ifor(i=0;i/* 8.085 编写函数将一个NxN的二维数组a的元素按列向上轮转1位。
例如:轮转前的数组
轮转后的数组
1 2 3
4 5 6
4 5 6 ---> 7 8 9
7 8 9
1 2 3 */ void turningUp(char a[N][N]) { int b[N][N],i,j; for(i=0;ifor(i=0;i/********** 8.103 编写函数,求整数m和n的最大公约数, 并作为函数的返回值。 **********/
int gdc(int m, int n) {
int a,r;
if(ma=m,m=n,n=a;
while((r=m%n)!=0)
{
m=n;n=r;
}
return (n); }
/********** 【习题8.105】请编写一个函数findmax(int []s, int n),返回数组s中
n(>0)个整数中的最大值。注意:要求在函数中采用指针(而不是下标)来 处理数组元素。 **********/ int findmax(int s[], int n)
/* 返回s中n(>0)个整数的最大值。
注意:要求在函数中采用指针(而不是下标)来处理数组元素。 */ { int i,m=*(s+i); for(i=0;*(s+i)!='\0';i++) if(m
/********** 【习题8.124】请编写一个函数min3adj(int s[], int n),数组s中 有n(>0)个整数,返回在s中相邻三个数的和中的最小值。 **********/ int min3adj(int s[], int n)
/* 数组s含n(>=3)个整数,
返回在s中相邻三个数的和中的最小值。 */ { int i,j; int sum[20]={0};int min = 0; for(i=0;ifor(j=0;j<3;j++ )
{
sum[i] += s[i+j];
} } sum[i+1]='\0'; min = sum[0]; for(i=0;iif(sum[i]{
min = sum[i];
} } return min; }
/********** 【习题8.132】编写函数,通过指针参数sum将x和y的 和赋给相应实际参数。例如,若x=1
34、y=378,则sum 的实参变量被赋值512。 **********/ void func(int x, int y, int *sum) { *sum=x+y;
}
/********** 【习题8.136】编写函数,返回指针参数x和y所指向的 变量的值之和。 **********/ int func(int *x, int *y) { return(*x+*y); }
/********** 【习题8.138】编写函数,比较指针参数x和y分别 指向的变量,若前者的值较大,则交换两者的值, 并返回1;否则无须交换,返回0。 **********/ int func(int *x, int *y) { int m; if(*x>*y) {m=*x; *x=*y; *y=m; return(1); } else
return(0);
}
/********** 【习题8.143】假设指针a指向某数组中的一个元素。 编写函数,在从元素*a开始的n个元素范围内,向后 查找给定值x,一旦找到值等于x的元素,则返回该元 素的序号;若找不到,则返回0。例如,假定a指向的 10个元素依次为5,6,3,0,-4,8,9,-6,8,-7,若x=5, 则返回1;若x=8,则返回6;若y=4,则返回0。 **********/ int func(int n, int *a, int x) { int i; for(i=0;*(a+i)!='\0';i++) if(*(a+i)==x) return(i+1); return(0); }
/********** 【习题8.146】假设指针a指向某数组中的一个元素。 编写函数,对从元素*a开始的n个元素,统计并返回 值为x的元素个数(若不存在这样的元素,则返回0)。 **********/ int func(int n, int *a, int x) { int i,k; for(i=0;*(a+i)!='\0';i++) if(*(a+i)==x) k++; return(k); return(0); }
/********** 【习题8.203】编写函数,返回指针参数s所指向的字 符串的长度。例如,若该串为"I am a student.", 则函数返回值是15。注意:字符串结束符是'\0',不 计入长度。不允许调用库函数strlen()。 **********/ int func(char *s) { int i; for(i=0;*(s+i)!='\0';i++) ; return(i); }
/********** 【习题8.212】编写函数,在指针参数s所指向的字 符串中顺序查找由c指定的字符。一旦找到,则返回 该字符在串中的序号(串的首个字符的序号为1), 否则返回0。例如,若该串为"I am a student.", c='t',则函数返回值为9。注意:字符串结束符是 '\0',不允许调用字符串库函数。 **********/ int func(char *s, char c) {
int i;
for(i=0;*(s+i)!='\0';i++)
if(*(s+i)==c)
return(i+1);
return(0); }
/********** 【习题8.215】编写函数,在指针参数s所指向的字 符串中统计并返回由c指定的字符的个数。例如,若 该串为"I am a student.",c='t',则函数返回值
为2。注意:字符串结束符是'\0',不允许调用字符 串库函数。 **********/ int func(char *s, char c) { int i,k;
for(i=0;*(s+i)!='\0';i++)
if(*(s+i)==c)
k++;
return(k);
return(0); }
/********** 【习题8.222】编写函数,复制指针参数s指向的字 符串到由指针参数t已经指向的存储区域。注意: 字符串结束符是'\0',不允许调用字符串库函数。 **********/ void func(char *s, char *t) { int i; for(i=0;*(s+i)!='\0';i++) *(t+i)=*(s+i); }
/********** 【习题8.225】编写函数,由指针参数s指向的字 符串头n个字符构造一个字符串,并存储到到由指 针参数t已经指向的存储区域。例如,若s指向的 字符串为"I am a student.",n=4,则t指向的 串为"I am"。注意:字符串结束符是'\0',不允 许调用字符串库函数。 **********/ void func(char *s, int n, char *t) { int i; for(i=0;i/********** 【习题8.228】编写函数,由指针参数s指向的字 符串后n个字符构造一个字符串,并存储到到由指 针参数t已经指向的存储区域。例如,若s指向的 字符串为"I am a student.",n=8,则t指向的 串为"student."。注意:字符串结束符是'\0', 不允许调用字符串库函数。 **********/ void func(char *s, int n, char *t) {
int i,j,n1;
while(s[i]) {
i++; } n1=i; for(j=0,i=n1-n;s[i]!='\0';i++)
t[j++]=s[i];
t[j]='\0'; }
/********** 【习题8.231】编写函数,由指针参数s指向的字 符串中第i个字符开始的n个字符构造一个字符串, 并存储到到由指针参数t已经指向的存储区域。例 如,若s指向的串为"I am a student.",i=8, n=7,则t指向的串为"student"。注意:字符串 结束符是'\0',不允许调用字符串库函数。 **********/ void func(char *s, int i, int n, char *t) { int j; for(j=0;j/********** 【习题8.234】编写函数,通过将s字符串中所有小写 字母转换成大写字母,构造一个字符串并存储在t已经 指向的存储区域,但原来的s串不改变。例如,若s字 符串为"I am a student.",则构造的t串为"I AM A STUDENT.”。 **********/ void func(char *s, char *t) { int i; for(i=0;*(s+i)!='\0';i++) if((*(s+i)>='A')&&(*(s+i)<='Z')) *(t+i)=*(s+i); else *(t+i)=*(s+i)-32;
}
/********** 【习题8.237】编写函数,通过将s字符串中所有大写 字母转换成小写字母,构造一个字符串并存储在t已经 指向的存储区域,但原来的s串不改变。例如,若s字 符串为"I Am a Student.",则构造的t串为"i am a student.”。 **********/ void func(char *s, char *t) {
int i; for(i=0;*(s+i)!='\0';i++) if((*(s+i)>='a')&&(*(s+i)<='z')) *(t+i)=*(s+i); else *(t+i)=*(s+i)+32; }
/********** 【习题8.243】编写函数,在字符串s中顺序查找字 符串t,若找到,则返回其出现的位置,否则返回0。 例如,设s="I am a student.",若t="stu",则返
回值是8;若t="an",则返回值是0。注意:字符串 结束符是'\0',不允许调用字符串库函数。 **********/ int func(char *s, char *t) { int i=0,j=0,n,m; while(s[i])
i++; n=i; while(t[j]) j++; m=j; for(i=0;i{
for(j=0;s[i+j]==t[j];j++)
if(j>=m-1) return i+1;
}
return 0; }
/********** 【习题8.246】假设字符串中每个连续字母序列称为 “单词”。编写函数,在字符串s中顺序获取每个单 词,依次存入w指示的二维数组,并返回单词个数。 例如,若有s="I am a student",则w={"I","am", "a","student"}。注意:字符串结束符是'\0',不 允许调用字符串库函数。 **********/ int func(char *s, char (*w)[10]) { int i,j=0,n=0; for(i=0;*(s+i)!='\0';i++) { if((*(s+i)>='a'&&*(s+i)<='z')||(*(s+i)>='A'&&*(s+i)<='Z')) {
*(*(w+j)+n)=*(s+i), n++;
if(!((*(s+i+1)>='a'&&*(s+i+1)<='z')||(*(s+i+1)>='A'&&*(s+i+1)<='Z')))
*(*(w+j)+n)='\0',j++,n=0;
}
}
return(j); }
/********** 【习题8.282】编写函数,查找并返回p指示的二维数 组中的元素最大值。例如,二维数组的元素值依次为 {{45,38,-6,78},{34,48,70,4},{-9,0,4,20}},则 函数返回值为78。 **********/ int func(int (*p)[4], int n) /* 求二维数组中的最大值 */ { int i ,j,min=p[0][0]; for(i=0;ifor(j=0;j<4;j++)
if(p[i][j]>min)
min=p[i][j];
return(min); }
/********** 【习题8.285】编写函数,依次对p指示的二维数组的 每一行元素值求和,并存入数组sum中。例如,若二维 数组的元素值依次为
{{45,38,-6,78},{34,48,70,4},{-9,0,4,20}}, 则sum[0..2]={155,156,15}。 **********/ void func(int (*p)[4], int n, int *sum) /* 求二维数组中各行元素值的和 */ {
int i,j;
for(i=0;isum[i]=*(*(p+i)+0)+*(*(p+i)+1)+*(*(p+i)+2)+*(*(p+i)+3);
}
/********** 【习题8.288】编写函数,依次对p指示的二维数组的 每一列元素值求平均值,并存入数组avg中。例如, 若二维数组的元素值依次为
{{45,38,-6,78},{34,48,70,4},{-9,0,4,20}}, 则avg[0..2]={23.33,28.67,34.00}。 **********/ void func(int (*p)[4], int n, float *avg) /* 求二维数组中各列元素值的平均值 */ { int i,j;
for(j=0;j<4;j++)
avg[j]=0;
for(i=0;ifor(j=0;j<4;j++)
avg[j]=avg[j]+p[i][j];
for(j=0;j<4;j++)
avg[j]=avg[j]/n; }
/********** 【习题9.023】结构体类型定义如下:
struct date{int year; int month; int day;}; //定义日期结构体类型
struct student
{ char name[20];
struct date birth; //出生日期
}; 结构体数组s存储了n个人的名字和出生日期。写一函数,求这n个人中年龄最大 (即出生日期最小)者的姓名。 **********/ char *oldest(student s[], int n) { int i; struct student *p;
p=&s[0];
for(i=1;i{ if(s[i].birth.year
{ p=&s[i]; continue; }
if(s[i].birth.year==(*p).birth.year)
{ if(s[i].birth.month
{ p=&s[i]; continue;}
if(s[i].birth.month==(*p).birth.month)
{ if(s[i].birth.day
p=&s[i];
}
}
}
return(p->name); }
/********** 【习题9.025】结构体类型定义如下:
struct date{int year; int month; int day;}; //定义日期结构体类型
struct student
{ char id[10];
//学号
char name[20];
//姓名
struct date birth; //出生日期
}; 结构体数组s存储了n个人的学号、名字和出生日期。写一函数,以结构体的形式 返回这n个人中年龄最大(即出生日期最小)者的信息。 **********/ struct student oldest(struct student s[], int n) { int i; struct student *p;
p=&s[0];
for(i=1;i{ if(s[i].birth.year
{ p=&s[i]; continue; }
if(s[i].birth.year==(*p).birth.year)
{ if(s[i].birth.month
{ p=&s[i]; continue;}
if(s[i].birth.month==(*p).birth.month)
{ if(s[i].birth.day
p=&s[i];
}
}
} return(*p); }
/********** 【习题9.027】结构体类型定义如下:
struct student
{ char id[10];
//学号
char name[10]; //姓名
int score[5]; //各门课成绩
}; 结构体数组s存储了n个学生的学号、名字和各门课成绩。编写 函数,返回这n个人中第i门课成绩最高者的学号。 **********/ char *best(struct student s[], int n, int i) { int j,k;
k=0;
for(j=1;j{
if(s[k].score[i]
k=j;
}
return s[k].id; }
/********** 【习题9.029】结构体类型定义如下:
struct student
{ char id[10];
//学号
char name[10]; //姓名
int score[5]; //各门课成绩
}; 结构体数组s存储了n个学生的学号、名字及其5门课成绩。编写 函数,返回这n个人中5门课成绩总分最高者的学号。 **********/ char *best(struct student s[], int n) { int i,j,k,sum[10]={0};
k=0;
for(i=0;ifor(j=0;j<5;j++)
sum[i]=sum[i]+s[i].score[j];
for(i=1;i{
if(sum[k]k=i;
}
return s[k].id; }
/********** 【习题9.033】日期和链表结点的结构体类型定义如下:
struct date{int year; int month; int day;}; //日期结构体类型
struct studentNode
//链表结点的结构体类型
{ char name[10];
//人名
struct date birth; //出生日期
struct studentNode *next;
}; 结构体链表L存储了n个人的名字和出生日期。写一函数,求这n个人中 年龄最大(即出生日期最小)者的名字。 **********/ char *oldest(struct studentNode *L) /* 若L是空表,则返回空指针null
否则返回表中年龄最大者的名字
*/ {
struct studentNode *p; if(L==NULL) return 0;
p=L;
for(L=L->next;L!=NULL;L=L->next)
{
if(p->birth.year>L->birth.year)
{
p=L;
}
if(p->birth.year==L->birth.year)
{
if(p->birth.month>L->birth.month)
{
p=L;
}
if(p->birth.month==L->birth.month)
{
if(p->birth.day>L->birth.day)
{
p=L;
}
}
}
}
return p->name;
}
/********** 【习题9.053】结构体类型定义如下:
struct person
{ int
id;
//员工号
char name[10]; //姓名
int
age;
//年龄
char sex;
//性别
}; 结构体数组personnel[n]存储了n位员工的信息。 写一函数,返回年龄在a及以上的员工数。 **********/ int count(struct person personnel[], int n, int a) { }
/********** 【习题9.055】结构体类型定义如下:
struct person
{ int
id;
//员工号
char name[10]; //姓名
int
age;
//年龄
char sex;
//性别
}; 结构体数组personnel[n]存储了n位员工的信息。 写一函数,返回年龄在a及以上的x性别的员工数。 **********/ int count(struct person personnel[], int n, int a, char x) { int i,sum=0;
for(i=0;iif(personnel[i].age>=a)
if(personnel[i].sex==x)
sum=sum+1; return sum; }
/********** 【习题9.063】结构体类型定义如下:
struct course
{ int
cID;
//课程号,取值0~99
char name[10]; //课程名
float credit;
//学分,取值0~5
int
semester; //学期,取值1~8
}; 结构体数组c存储了n门课程的信息。写一函数,求学期s的总学分。 **********/ float creditSum(struct course c[], int n, int s)
{ int i;
float sum=0;
for(i=0;iif(c[i].semester==s)
sum=sum+c[i].credit;
return sum;
}
/********** 【习题9.073】课程链表结点的结构体类型定义如下:
struct courseNode
//课程链表结点的结构体类型
{ int
cID;
//课程号,取值0~99
char name[10]; //课程名
float credit;
//学分,取值0~5
int
semester; //学期,取值1~8
struct courseNode *next;
}; 结构体链表Lc存储了各学期多门课程的信息。写一函数,求学 期s的总学分。 **********/ float creditSum(struct courseNode *Lc, int s) /* 若Lc是空表,则返回0;
否则返回学期s的总学分
*/ { float sum=0;
if(Lc==NULL)
return 0.0;
else
{while(Lc!=NULL)
{if(s==(*Lc).semester)
sum=sum+(*Lc).credit;
Lc=(*Lc).next;
}
return sum;
} }
/********** 【习题9.133】日期和结构体类型定义如下:
struct date{int year; int month; int day;}; //日期结构体类型
struct student
//结构体类型
{ char name[10];
//人名
struct date birth; //出生日期
}; 结构体数组s存储了n个人的名字和出生日期。写一函数,由数组s中n个人 的信息及其顺序构造相应的链表。链表的结点的结构体类型定义如下:
struct studentNode
//结构体类型
{ char name[10];
//人名
struct date birth; //出生日期
struct studentNode *next
}; **********/
struct studentNode *CreateLinkList(struct student s[], int n) {
int i,j=0;
struct studentNode *head;
struct studentNode *p1,*p2;
if(n==0) return NULL;
while(j{p1=(struct studentNode *)malloc(sizeof(struct studentNode));
if(j==0) head=p1;
else (*p2).next=p1;
p2=p1;
for(i=0;i<10;i++)
(*p1).name[i]=s[j].name[i];
(*p1).birth.year=s[j].birth.year;
(*p1).birth.month=s[j].birth.month;
(*p1).birth.day=s[j].birth.day;
j++;
}
(*p2).next=NULL;
return(head); }
/********** 【习题9.173】课程链表结点的结构体类型定义如下:
struct courseNode
//课程链表结点的结构体类型
{ int
cID;
//课程号,取值0~99
char name[10]; //课程名
float credit;
//学分,取值0~5
int
semester; //学期,取值1~8
struct courseNode *next;
}; 结构体链表Lc存储了多门课程的信息。写一函数,将课程号为c的 课程的学分修改为t。 **********/
struct courseNode *creditChange(struct courseNode *Lc, int c, float t) /* 若课程c不存在,则修改不成功,返回null;
否则修改该课程的学分为t,返回指向该课程结点的指针。
*/ {
struct courseNode *p1;
p1=Lc;
while(p1!=NULL)
{
if(p1->cID==c)
{
p1->credit=t;break; }
else
p1=p1->next;
}
return p1; }
/********** 【习题9.183】课程链表结点的结构体类型定义如下:
struct courseNode
//课程链表结点的结构体类型
{ int
cID;
//课程号,取值0~99
char name[10]; //课程名
float credit;
//学分,取值0~5
int
semester; //学期,取值1~8
struct courseNode *next;
}; 结构体链表Lc存储了多门课程的信息。写一函数,将课程号为c的 课程结点删除。 **********/
struct courseNode *deleteCourse(struct courseNode **Lc, int c) /* 若在链表Lc中课程c不存在,则删除不成功,返回null;
否则从链表Lc中删除该课程结点,并返回指向该课程结点的指针。
*/ { struct courseNode *p1,*p2,*head,*t;
p1=p2=*Lc;
while(c!=p1->cID&&p1->next!=NULL)
{
p2=p1;p1=p1->next;}
if(c==p1->cID)
{ t=p1;
if(p1==*Lc)
*Lc=p1->next;
else
p2->next=p1->next;
return(t);
}
else
return(NULL); }
/********** 【习题9.302】单向链表的结点类型定义如下:
struct node{
char ch;
struct node *next;
}; 编写函数,对单向链表L实现就地逆置,即将所有结点 的指针反向,原链头当作链尾,原链尾当作链头,并返 回逆置后链表的头指针。 **********/ struct node *inverse(struct node *L) {
struct node *p1=L,*p2;
int i,n=0;
char t;
while(p1!=NULL)
{p1=p1->next;
n++;
}
p1=L;
for(i=0;i{
while(p1!=NULL)
{ p2=p1->next;
if((p1->ch)ch))
{t=p1->ch,p1->ch=p2->ch,p2->ch=t;}
if(p2->next!=NULL)
p1=p1->next;
else p1=NULL;
}
p1=L;
}
return L;
}
/********** 【习题9.352】单向链表的结点类型定义如下:
struct node{
char ch;
struct node *next;
}; 编写函数,对单向链表L实现排序,即按结点的ch值, 从小到大重构链表L,并返回排序后的链表的头指针。 **********/ struct node *sorting(struct node *L) /* 对单向链表L实现从小到大排序,
并返回重构后的链表的头指针。
*/ {
struct node *p1,*p2; char t;
C Anyview 7-9章作业参考答案
/********** 【习题7.010】写一函数求3个整数中最小的数。 **********/ int min(int x, int y, int z) /* 返回3个整数x,y和z中最小的数 */ {
if(x>y)
x=y;
if(x>z)
x=z;
return x;
}
/********** 【习题7.020】编写函数,求用1元、5元和10元三种纸币 支付n元钱共有多少种支付法?
例如,16元可有6种支付方法:
方法
10元
0
0
0
0
5元
0
0
1元
16 11
1 **********/ int change(int n) { int i,j,k,m=0; for(i=0;i<=n;i++)
for(j=0;j<=n/5;j++)
for(k=0;k<=n/10;k++)
if(i+5*j+10*k==n)
m++;
return m;
} /********** 【习题7.030】先编写一个判断素数的函数。再编写一个函数 将一个偶数表示为两个素数之和,并返回其中较小的素数。
注:素数指只能被1和自身整除的正整数。规定0,1不是素数。 **********/ int prime(int n)
/* 判断素数,如果是素数返回1,不是素数则返回0 */ { int t;
if(n==1)
return 0;
for(t=2;t<=(n/2);t++)
if(n%t==0)
return 0;
return 1; }
int f(int i)
/* 将偶数i表示为两个素数之和,返回其中较小的素数*/ { int n; for(n=3;n<=i;n++) if(prime(i-n)&&prime(n)) return n; }
/********** 【习题7.050】编写函数,将字符串中ASCII码最小的字符 放在第一个字符位置,其余字符依次往后移。 **********/ void func(char *str) /* 将字符串str中ASCII码最小的字符放在第一个 */ /* 字符位置,其余字符依次往后移。
*/ { int i=1,m=0,k; for(m=0,i=1;str[i]!='\0';i++) { if(str[m]>str[i]) m=i; } k=str[m]; for(i=m-1;i>=0;i--) str[i+1]=str[i]; str[0]=k; }
/**********
7.051 系统给定外部字符串s和整型数组c[26](不需 要自行定义)。编写程序,将字符串s中26个字母(不 区分大小写)出现的次数依次统计到数组c中。例如, 当s=“AbcijKaBcdEXyzuvwx”时,数组c的26个元素 值依次为:2 2 2 1 1 0 0 0 1 1 1 0 0 0 0 0 0 0 0 0 1 1 1 2 1 1。 **********/ void main() { int i,j; for(j=0;j<26;j++) { c[j]=0; for(i=0;s[i]!='\0';i++) if(s[i]=='A'+j||s[i]=='a'+j) c[j]++; } }
/********** 【习题7.060】编写函数将一个nxn的二维数组按“次对角线”翻转。 例如:翻转前的数组
翻转后的数组
1 2 3
9 6 3
4 5 6 ---> 8 5 2
7 8 9
7 4 1 **********/ void invert(char a[N][N]) { int i,j; int b[N][N]; for(i=0;ifor(i=0;i}
/********** 【习题7.064】编写函数将一个NxN的二维数组“水平”翻转。 例如:翻转前的数组
翻转后的数组
1 2 3
7 8 9
4 5 6 ---> 4 5 6
7 8 9
1 2 3 **********/ void invertH(char a[N][N]) { int i,j; int b[N][N]; for(i=0;i/********** 【习题7.065】编写函数将一个NxN的二维数组“垂直”翻转。 例如:翻转前的数组
翻转后的数组
1 2 3
3 2 1
4 5 6 ---> 6 5 4
7 8 9
9 8 7 **********/ void invertV(char a[N][N]) {
int i,j; int b[N][N]; for(i=0;i/********** 【习题7.068】编写函数将一个NxN的二维数组的 周边元素“逆时针”轮转1位。
例如:轮转前的数组
轮转后的数组
1 2 3
2 3 6
4 5 6 ---> 1 5 9
7 8 9
4 7 8 **********/ void turningAnticlockwise(char a[N][N]) { int i;
char t=a[0][0];
for(i=0;ia[0][i]=a[0][i+1];
for(i=0;ia[i][2]=a[i+1][2];
for(i=0;ia[2][2-i]=a[2][2-i-1];
a[2][0]=a[1][0];
a[1][0]=t;
}
/********** 【习题7.072】编写函数将一个NxN的二维数组a的元素 按行向右轮转1位。
例如:轮转前的数组
轮转后的数组
1 2 3
3 1 2
4 5 6 ---> 6 4 5
7 8 9
9 7 8 **********/ void turningRight(char a[N][N]) { int b[N][N],i,j; for(i=0;ifor(i=0;i/********** 【习题7.075】编写函数将一个NxN的二维数组a的元素 按行向左轮转1位。
例如:轮转前的数组
轮转后的数组
1 2 3
2 3 1
4 5 6 ---> 5 6 4
7 8 9
8 9 7 **********/ void turningLeft(char a[N][N]) { int b[N][N],i,j; for(i=0;ifor(i=0;i/********** 【习题7.082】编写函数将一个NxN的二维数组a的元素 按列向下轮转1位。
例如:轮转前的数组
轮转后的数组
1 2 3
7 8 9
4 5 6 ---> 1 2 3
7 8 9
4 5 6 **********/ void turningDown(char a[N][N]) {
int b[N][N],i,j; for(i=1;ifor(i=0;i/********** 【习题7.085】编写函数将一个NxN的二维数组a的元素 按列向上轮转1位。
例如:轮转前的数组
轮转后的数组
1 2 3
4 5 6
4 5 6 ---> 7 8 9
7 8 9
1 2 3 **********/ void turningUp(char a[N][N]) { int b[N][N],i,j; for(i=0;ifor(i=0;i/********** 【习题7.103】编写函数,求整数m和n的最大公约数, 并作为函数的返回值。 **********/
int gdc(int m, int n) {
int a,r;
if(ma=m,m=n,n=a;
while((r=m%n)!=0)
{
m=n;n=r;
}
return n; }
/********** 【习题7.105】 编写函数,求整数m和n的最小公倍数, 并作为函数的返回值。 **********/ int lcm(int m, int n) {
int t,r,h;
h=m*n;
if(m{t=m;m=n;n=t;}
while((r=m%n)!=0)
{
m=n;n=r;
}
return h/n; }
/********** 7.110 系统给定外部字符数组变量s和数组长度n(不需要自行 定义)。main函数的功能是:把字符串s中所有小写字母转换为 大写字母,其他字符不变。例如,当s="68abcdEFGhijkLM86" 时,转换后s="68ABCDEFGHIJKLM86"。
请仅在空缺处填入合适内容,使其实现上述功能。 **********/ void main() {
int i;
/*** 1 ***/i=0; ;
while(i{
if(*(s+i)>='a' && *(s+i)<='z')
*(s+i)=/*** 2 ***/*(s+i)-32 ;
/*** 3 ***/ i++;
} }
/********** 【习题7.115】 编写函数,将两个两位数的正整数a、b合并形成 一个整数c且作为函数值返回。合并的方式是:将a的十位和个位 数分别作为c的千位和十位数,b的十位和个位数分别作为c的百位 和个位数。例如,若a=45,b=12,则该函数返回值为4152。 **********/
int func(int a, int b) { int c; c=a/10*1000+a%10*10+b/10*100+b%10; return c; }
/********** 7.120 系统给定外部长整型变量n和字符数组变量s(不需要自行 定义)。main函数的功能是:把n的整数值转换成字符串,并逆序 保存在s中。例如,当n=20120826时,由n转换得到s="62802102"。 请仅在空缺处填入合适内容,使其实现上述功能。 **********/ void main() {
int i=0;
while( /*** 1 ***/n>0 )
{
s[i]= /*** 2 ***/n%10+'0' ;
/*** 3 ***/ n/=10;
i++;
}
s[i]='\0'; }
/********** 7.121 系统给定外部长整型变量n和字符数组变量s(不需要自行 定义)。main函数的功能是:把n的整数值转换成字符串,并保存 在s中。例如,当n=20120826时,由n转换得到s="20120826"。 请仅在空缺处填入合适内容,使其实现上述功能。 **********/ void main() {
int i=0,k;
char c[10];
while( /*** 1 ***/ 10*n/10!=0)
{
c[i]= /*** 2 ***/n%10 ;
n/=10;
i++;
}
s[i--]='\0';
k=i;
while(i>=0)
{
s[i]=/*** 3 ***/c[k-i]+'0';
i--;
} }
/********** 【习题7.125】编写函数,对非负浮点数r的值的第三位小数四舍五入, 返回保留2位小数的值。例如:若r的值为8.32488,则函数返回8.32; 若r的值为8.32533,则返回8.33。 **********/ float func(float r) { int a,b; a=r*1000; b=a%10; if(b<5) r=(a-b)*0.001; else r=(a-b+10)*0.001; return r; }
/********** 【习题7.135】假设n是一个k(k≥2)位的正整数,编写函数, 求出由n的低k-1位构成的数并作为函数值返回。例如:若n值 为5923,则函数返回923;若n值为923,则函数返回23。 **********/ int func(int n) {
int i,j,k=n,m=1;
while(k>=10)
k/=10,i++; for(j=1;j<=i;j++) m=m*10; n=n-k*m;
return n; }
/********** 【习题7.175】编写函数,求n以内(不包括n)同时能被3与7 整除的所有自然数之和的平方根,并作为函数值返回。例如, 若n为100时,函数返回值应为14.49138。 **********/ float func(int n) { int i;float s; for(i=0;i{if(i%3==0&&i%7==0)
s=s+i; }
s=sqrt(s);
return(s); }
/********** 【习题7.184】编写函数,根据公式s=1+1/(1+2)+1/(1+2+3)+ „„1/(1+2+3+„+n)计算s,并作函数值返回。例如:若n的值 为11时,函数的值为1.833333。 **********/ float func(int n) { int i; float j=1.0,s=1.0; for(i=2;i<=n;i++) {j=j+i; s=s+1/j; } return (s); }
/********** 【习题7.187】编写函数,计算并输出下列级数和: 1/(1*2)+1/(2*3)+1/(3*4)+ „ +1/(n*(n+1)),
并返回结果。例如,当n=10时,函数值为0.90909。 **********/ float func(int n) { int i; float x,y; for(i=1;i<=n;i++) {x=i*(i+1); y=y+1/x; } return(y); }
/********** 【习题7.195】编写函数,求m!/(n!(m-n)!)的值,结果由函数值
返回。m与n为两个正整数且要求m>n。例如:m=12,n=8时,运行 结果为495.000000。 **********/ float func(int m, int n) { int i,j,k,l; float x=1.0,y=1.0,z=1.0; if(m<=n) l=m,m=n,n=l; for(i=1;i<=m;i++) x=x*i; for(j=1;j<=n;j++) y=y*j; for(k=1;k<=m-n;k++) z=z*k ; z=x/(z*y); return(z);
}
/********** 【习题7.205】编写函数,计算并返回给定整数n除了1与自身 之外的所有因子之和。例如,若n=8,则函数返回6(=2+4)。 **********/ int func(int n) { int i,j,k; for(i=1;i<=0.5*n;i++)
for(j=1;j<=n;j++)
if(i*j==n)
k=k+i+j;
k=k-1-n;
k=k/2;
return(k);
}
/********** 【习题7.255】编写函数,根据以下公式返回π的值
π/2 = 1+1!/3+2!/(3*5)+...+n!/(3*5*7*...*(2*n+1)) 要求满足精度eps,即一旦有小于eps的项值加入后停止迭代。 例如,若精度eps=0.0005,则返回值为3.141106。 **********/ float func(float eps) { int i; float x=1,y=1,z; for(i=1;(x/y)>=eps;i++) {x=x*i; y=y*(2*i+1); z=z+x/y;} z=2*z+2; return(z);
}
/********** 【习题7.265】编写函数,将数组s所存字符串中下标和ASCII码 均为偶数的字符,依次存入数组t中,并构成一个新串。例如, 若s中的字符串值为ABCD123456,则t中的串值应为246。 **********/ void func(char s[], char t[]) { int i,j,m=0; for(i=0;s[i]!=0;i++)
if((i%2==0)&&(s[i]%2==0)) t[j]=s[i],j++;
}
/********** 【习题7.275】假定字符串s中可能含有字符'*'。请编写函数, 若字符串s的尾部连续的'*'多于n个,则删除多余的'*'。例如, 若s="*****A*BCDE**F*******"且n=4,则调用函数后,字符串 s="****A*BCDE**F****";若n≥7,则字符串s中的内容不变。 注意:函数中不得调用C语言提供的字符串函数。 **********/ void func(char s[], int n) { int i,j,k,d=0,c=0,t=0; while(s[d++]) c++; for(i=c-1;i>=0;i--)
{if(s[i]=='*')
t++;
else break;}
if(t>n)
{k=t-n;
s[c-k]='\0';}
}
/********** 【习题7.315】编写函数,求出1到n之间(含n)能被7或11整除的 所有整数并依次存入数组a中,函数值为这些数的个数。例如, 若n=15,则依次存入数组a中的数为
7、11和14,函数值为3。 **********/ int func(int n, int a[]) { int i,j=0; for(i=1;i<=n;i++) if((i%7==0)||(i%11==0)) a[j]=i,j++; return(j); }
/********** 【习题7.317】编写函数,求出1到n之间(含n)都能被c和d整除 的所有整数并依次存入数组a中,函数值为这些数的个数。例如, 若n=20,c=2,d=3,则依次存入数组a中的数为
6、12和18,函 数值为3。 **********/ int func(int n, int c, int d, int a[]) {
int i,j;
for(i=1;i<=n;i++)
if((i%c==0)&&(i%d==0))
a[j]=i,j++;
return(j); }
/********** 【习题7.325】假设数组a存放了n个人的年龄。编写函数,用 数组c统计各年龄段的人数,其中c[0]为0至9岁年龄段的人数, c[1]为10至19岁年龄段的人数,c[2]为20至29岁年龄段的人 数,其余依此类推,c[10]为100岁(含100)以上年龄的人数。 **********/ void func(int n, int a[], int c[]) {
int i,b; for(i=0;i<=10;i++) c[i]=0;
for(i=0;i=100) c[10]++; else { b=a[i]/10; c[b]++; }} }
/********** 【习题7.335】假设字符数组a中存放了按由小到大连续存放的 字符构成的字符串(后跟一个'\0'作为结束符)。编写函数, 删去字符串中所有重复的字符(各自只保留一个),并使得保 留的字符仍构成一个字符串(连续存放,'\0'作为结束符)。
函数返回a中保留的字符串长度。例如,若a中的字符串值为:
AAABBCDFFFHHHKLMMM 则删除重复字符之后,函数返回值为9,a中的字符串值为:
ABCDFHKLM **********/ int func(char a[]) { int i; //while(a[i]!='\0') //i++; char c[26];int j=1,k; c[0]=a[0]; for(i=1;a[i]!='\0';i++) if(a[i]!=a[i-1]) c[j]=a[i],j++; while(c[k]!='\0') k++; for(i=0;i<=k;i++) a[i]=c[i]; return(k);
}
/********** 【习题7.345】假设字符数组s中存放了一行字符串,含有由小写 字母组成的若干单词,单词之间由若干个空格隔开(串的开头没 有空格)。编写函数,统计一行字符串中单词的个数,并作为函 数值返回。 **********/ int func(char s[]) { int i,j; for(i=0;s[i]!=0;i++) if(s[i]==' ') j++; j+=1; for(i=0;s[i]!=0;i++) if((s[i]==' ')&&(s[i+1]==' ') ) j--; return(j); }
/********** 【习题7.355】假定字符串s中可能含有字符'*'。请编写函数, 将字符串s中前导'*'全部移到字符串的尾部。例如,若s的串
值为***A*BC*DEF*G**,移动后,串值应为A*BC*DEF*G*****。 注意:不得调用C语言提供的字符串函数。 **********/ void func(char s[]) { int i,j=0,k=0; char b[100];
for(i=0;s[i]!='\0';i++)
{
if(s[i]=='*')
k++;
else break;
} for(i=k;s[i]!='\0';i++)
{
b[j]=s[i];
j++;
} for(i=0;i{
if(is[i]=b[i];
else s[i]='*';
}
s[i]='\0';
}
/********** 【习题7.513】编写函数,计算并返回数组a中头n个 元素的乘积。
**********/ long func(int a[], int n) {
int i,s=1;
for(i=0;is=s*a[i];
return(s); }
/********** 【习题7.523】编写函数,计算并返回数组a中头n个 元素的平方和。
**********/ long func(int a[], int n) {
int i,s;
for(i=0;is=s+a[i]*a[i];
return (s); }
/********** 【习题7.533】假设某班选举班长,k位候选人的 号码分别为1至k,n张选票已存入数组v(每个元 素值在1至k之间)。编写函数,用数组c统计各位 候选人的得票(c[i]为i号候选人的得票数)。
**********/ void func(int v[], int n, int k, int c[]) { int i,j; for(j=0;j<=k;j++) c[j]=0; for(i=0;i/********** 【习题7.535】假设某班选举班长,k位候选人的 号码分别为1至k,n张选票已存入数组v(每个元 素值在1至k之间)。编写函数,用数组c统计各位 候选人的得票(c[i]为i号候选人的得票数),并 返回得票最高的人的号码。
**********/ int func(int v[], int n, int k, int c[]) {
int i,j,max; for(i=0;i<5;i++)
c[i]=0; for(i=0;ic[v[i]]++;
max=c[0]; for(i=1;i<=k;i++)
if(max{
j=i;
max=c[i];
}
return j;
}
/********** 【习题7.563】编写函数,把长整数n的各位数字从低 位到高位依次存储在数组d中,并返回n的位数。例如, 若n=2579,则n的位数为4,d[0..3]=9,7,5,2。 **********/ int func(long n, int d[]) {int i; while(n>0) {d[i]=n%10,i++; n=n/10; } return(i); }
/********** 【习题7.565】编写函数,把长整数n的各位数字从高 位到低位依次存储在数组d中,并返回n的位数。例如, 若n=2579,则n的位数为4,d[0..3]=2,5,7,9。 **********/ int func(long n, int d[]) { int i,j; int a[25]; for(i=0;n!=0;i++)
{
a[i]=n%10;
n=n/10;
}
j=i;
for(i=0;id[i]=a[j-i-1];
return j; }
/********** 【习题7.655】编写函数,用数组num统计字符串s中各元音字母 (即:A、E、I、O、U)的个数。注意:不分大、小写。例如, 若s="THIs is a book",则num[0..4]={1,0,2,2,0}。 **********/ void func(char *s, int *num) /* 功能:用数组num统计符串s中元音字母出现的个数 */ {
int i;num[0]=0, num[1]=0,num[2]=0,num[3]=0,num[4]=0;
for(i=0;s[i]!='\0';i++)
if((s[i]=='a')||(s[i]=='A'))
num[0]++;
for(i=0;s[i]!='\0';i++)
if((s[i]=='e')||(s[i]=='E'))
num[1]++;
for(i=0;s[i]!='\0';i++)
if((s[i]=='i')||(s[i]=='I'))
num[2]++;
for(i=0;s[i]!='\0';i++)
if((s[i]=='o')||(s[i]=='O'))
num[3]++;
for(i=0;s[i]!='\0';i++)
if((s[i]=='u')||(s[i]=='U'))
num[4]++;
}
/**【习题7.675】假设在数组s中存放了n位学生的成绩。 编写函数,用数组p统计各分数段的人数,其中p[0]为 不足60分的人数,p[1]为60至69分的人数,p[2]为70 至79分的人数,p[3]为80至89分的人数,p[4]为90至 100分的人数。 **********/ void func(int s[], int n, int p[]) {
int i;
for(i=0;i<5;i++)
p[i]=0;
for(i=0;i{if(s[i]<60)
p[0]++;
if((s[i]>=60)&&(s[i]<70))
p[1]++;
if((s[i]>=70)&&(s[i]<80) )
p[2]++;
if((s[i]>=80)&&(s[i]<90) )
p[3]++;
if((s[i]>=90)&&(s[i]<=100))
p[4]++;} }
/********** 【习题7.685】编写函数,从小到大依次求出能整除m的各整数, 并存放在数组d中,这些除数的个数由n返回。例如,若m=20,则 有6个数能整除它,依次是1,2,4,5,10,20。 **********/ void func(int m, int d[], int *n) { int i,j; for(i=1;i<=m;i++) if(m%i==0) d[j]=i, j++; *n=j; }
/********** 【习题7.755】通信时经常用到加密技术,把消息加密后再传输。 编写一个用于加密消息的函数,把字符串str中的小写字母改成
“(其ASCII码加上字符串key中每个字符ASCII码的平方)除以128 所得的余数”作为ASCII码对应的字符,其它的字符不变,其中 str称为消息原文,key称为密钥。 请思考:如何解密恢复原文,这种加密方法能准确地恢复原文吗? **********/ void func(char *str,char *key) /* 功能:用key作为密钥对字符串str进行加密处理 */ {
int i,j,k;
for(i=0;key[i]!='\0';i++)
k=k+key[i]*key[i];
for(j=0;str[j]!='\0';j++)
if((str[j]<='z')&&(str[j]>= 'a') )
str[j]=(str[j]+k)%128; }
int min(int x, int y, int z) /* 返回3个整数x,y和z中最小的数 */ {
if(x>y)
x=y;
if(x>z)
x=z;
return(x);
}
/********** 【习题8.011】请编写函数func(char s[], char t[], int n),
由数组s中长度为n的字符序列构造其逆序列,并存储在数组t中。 例如,由给定字符序列s="are"求得逆序列t="era";由s="time" 求得t="emit"。 **********/ void func(char s[], char t[], int n)
/* 数组s的前n个元素存放给定的字符序列,
数组t的前n个元素存放s的逆序列。
注意:数组的下标从0开始。 */ { int i; for(i=0;i}
/********** 【习题8.012】请编写函数func(char*s, char *t),由字符
串s构造其逆串t。例如,由给定串s="are"求得逆串t="era"; 由s="time"求得t="emit"。 **********/ void func(char *s, char *t)
/* s是给定字符串的起始地址,
t是求得s的逆串的起始地址 */ { int i,j; for(j=0;s[j]!='\0';j++) ; for(i=0;i/********** 【习题8.015】对长度为n的字符串s1,除首、尾字符外,将 其余字符按ASCII码降序排列,组合成一个新的字符串s2。 **********/ void func(char *s1, char *s2, int n) /* s1为字符串的起始地址,
s2为新字符串的起始地址,
n为字符串的长度。
要求:s1串不能发生改变,
s2串存放新的字符串。 */ { int i,j;
char t;
n=strlen(s1);
for(i=0;i*(s2+i)=*(s1+i);
for(j=1;jfor(i=1;i<=n-2-j;i++)
{ if(*(s2+i)
{ t=*(s2+i);
*(s2+i)=*(s2+i+1);
*(s2+i+1)=t;
} }}
/********** 【习题8.016】对字符串s1,除首、尾字符外,将其余字符 按ASCII码降序排列,组合成一个新的字符串s2。 **********/ void func(char *s1, char *s2) {int n; n=strlen(s1); int i,j,k; char t;
for(i=0;is2[i]=s1[i];
s2[i]='\0';
for(i=1;i{
k=i;
for(j=i+1;jif(s2[k]k=j;
t=s2[i];
s2[i]=s2[k];
s2[k]=t;
} }
/********** 【习题8.020】在字符串s中查找字符c,如果找到,返回字符c 首次出现在字符串s中的位置指针;否则,返回空指针NULL。 **********/ char *match(char *s, char c)
/* 返回字符在串s中首次出现的位置指针 */ {
int i;
for(i=0;s[i]!='\0';i++)
if(s[i]==c)
return(s+i);
return(NULL);
}
/* 8.030 先编写一个判断素数的函数。再编写一个函数将一个
偶数表示为两个素数之和,并返回其中较小的素数。
注:素数指只能被1和自身整除的正整数。规定0,1不是素数。
*/ int prime(int n)
/* 判断素数,如果是素数返回1,不是素数则返回0 */ { int t;
if(n==1)
return 0;
for(t=2;t<=(n/2);t++)
if(n%t==0)
return 0;
return 1; }
int f(int i)
/* 将偶数i表示为两个素数之和,返回其中较小的素数*/ {
int n; for(n=3;n<=i;n++) if(prime(i-n)&&prime(n)) return n; }
/********** 【习题8.033】编写函数,计算年份year中第yearday天相应的月 和日。例如,调用函数month_day(2000,61,&m,&d)之后,m=3, d=1,即2000年的第61天是3月1日。 **********/ int month_day(int year, int yearday, int *pmonth, int *pday) /* year是年,
yearday是天数,
若year和yearday合理,
则*pmonth和*pday是计算得出的月和日,函数返回1;
否则,函数返回0。 */ { int s[12]={31,28,31,30,31,30,31,31,30,31,30,31},m ;
if(year%4==0&&year%100!=0||year%400==0)
s[1]=29; if(year<1||yearday<1||(s[1]==28&&yearday>365)||(s[1]==29&&yearday>366))
return 0;
else
for(m=0;yearday-s[m]>0&&m<12;m++)
yearday-=s[m];
if(yearday==0)
{
m=m-1;
yearday=s[m];
}
*pmonth=m+1;
*pday=yearday;
return 1;
}
/********** 【习题8.044】请编写一个函数func,通过略去非数字字符,将字符串 s转换为一个整数(不得调用C语言提供的将字符串转换为整数的函数)。 **********/ long func(char *s)
/* s是一个数字字符串的地址,
函数返回值为由s含有的数字字符转换得到的数(包含正负数情况)
*/ { int i,j=1,k=0,flag=1; long n=0; for(i=0;s[i];i++) {
if(s[i]=='+'&&flag)
{
flag=0;
j=1;
}
if(s[i]=='-'&&flag)
{
flag=0;
j=-1;
}
if(s[i]>47&&s[i]<58)
{
n=n*10;
n=n+(s[i]-'0');
}
if(n) flag=0; } n=n*j; return n; }
/* 8.050 编写函数,将字符串中ASCII码最小的字符放在第一
个字符位置,其余字符依次往后移。
*/ void func(char *str) /* 将字符串str中ASCII码最小的字符放在第一个 */ /* 字符位置,其余字符依次往后移。
*/ { int i=1,m=0,k; for(m=0,i=1;str[i]!='\0';i++) { if(str[m]>str[i]) m=i; } k=str[m]; for(i=m-1;i>=0;i--) str[i+1]=str[i]; str[0]=k; }
/* 8.060 编写函数将一个nxn的二维数组按“次对角线”翻转。
例如:翻转前的数组
翻转后的数组
1 2 3
9 6 3
4 5 6 ---> 8 5 2
7 8 9
7 4 1 */ void invert(char a[N][N]) { int i,j; int b[N][N]; for(i=0;ifor(i=0;i/* 8.064 编写函数将一个NxN的二维数组“水平”翻转。
例如:翻转前的数组
翻转后的数组
1 2 3
7 8 9
4 5 6 ---> 4 5 6
7 8 9
1 2 3 */ void invertH(char a[N][N]) {
int i,j; int b[N][N]; for(i=0;i/* 8.065 编写函数将一个NxN的二维数组“垂直”翻转。
例如:翻转前的数组
翻转后的数组
1 2 3
3 2 1
4 5 6 ---> 6 5 4
7 8 9
9 8 7 */ void invertV(char a[N][N]) { int i,j; int b[N][N]; for(i=0;i/* 8.067 编写函数将一个NxN的二维数组的周边元素“顺时针”轮转1位。
例如:轮转前的数组
轮转后的数组
1 2 3
4 1 2
4 5 6 ---> 7 5 3
7 8 9
8 9 6 */ void turningClockwise(char a[N][N]) { int i,j,row=0,column=0; int tmp,t; int flag=1;
for(i=0;ifor(i=0;i/*8.068 编写函数将一个NxN的二维数组的周边元素“逆时针”轮转1位。
例如:轮转前的数组
轮转后的数组
1 2 3
2 3 6
4 5 6 ---> 1 5 9
7 8 9
4 7 8 */ void turningAnticlockwise(char a[N][N]) { int i;
char t=a[0][0];
for(i=0;ia[0][i]=a[0][i+1];
for(i=0;ia[i][2]=a[i+1][2];
for(i=0;ia[2][2-i]=a[2][2-i-1];
a[2][0]=a[1][0];
a[1][0]=t; }
/* 8.072 编写函数将一个NxN的二维数组a的元素按行向右轮转1位。
例如:轮转前的数组
轮转后的数组
1 2 3
3 1 2
4 5 6 ---> 6 4 5
7 8 9
9 7 8 */ void turningRight(char a[N][N]) { int b[N][N],i,j; for(i=0;ifor(i=0;i/* 8.075 编写函数将一个NxN的二维数组a的元素按行向左轮转1位。
例如:轮转前的数组
轮转后的数组
1 2 3
2 3 1
4 5 6 ---> 5 6 4
7 8 9
8 9 7 */ void turningLeft(char a[N][N]) {
int b[N][N],i,j; for(i=0;ifor(i=0;i/* 8.082 编写函数将一个NxN的二维数组a的元素按列向下轮转1位。
例如:轮转前的数组
轮转后的数组
1 2 3
7 8 9
4 5 6 ---> 1 2 3
7 8 9
4 5 6 */ void turningDown(char a[N][N]) { int b[N][N],i,j; for(i=1;ifor(i=0;i