printf("%8.2f",a[i]);
}
printf("\n");
}
思考:
此题中可以不用数组进行处理吗(进一步理解数组的特点。
)
8-5编写程序,从键盘输入某班学生C语言课程考试成绩,评定每个学生C语言成绩等级。
如果高于平均分10分,则等级为优秀;如果低于平均分10分,则等级为一般;否则等级为中等。
解:
#include""
#defineN3
voidmain()
{
inti,j;
floataverage,a[N],sum=0;
for(i=0;i{
scanf("%f",&a[i]);
sum=sum+a[i];
}
average=sum/N;
for(i=0;i{
if(a[i]>average+10)printf("a[%d]优秀\n",i);
elseif(a[i]elseprintf("a[%d]中等\n",i);
}
}
思考:
表示数组元素的a[i]一般称为什么变量它与一般变量有何区别
8-6某班期终考试有六门课程,编写程序计算每门课程的平均成绩。
进一步考虑全年级10个班的情况。
解:
#include""
#defineN30
#defineM6
voidmain()
{
inti,j;
floataverage[M],a[N][M],sum=0;
for(i=0;ifor(j=0;jscanf("%f",&a[i][j]);
for(j=0;j{
sum=0;
for(i=0;isum=sum+s[i][j];
average[j]=sum/N;
}
printf("6门课程的平均成绩分别为:
\n");
for(i=0;i{
printf("%f",average[i]);
}
printf("\n");
}
思考:
在此题中定义的数组a[N][M]中,N表示什么M表示什么若考虑全年级10个班的情况,程序应做哪些改进
8-7编写程序,将一个一维数组进行逆置。
例如,原来顺序为1,3,5,7,则逆置后的顺序为7,3,5,1.
解:
#include""
#defineN4
voidfun(inta[])
{
inti,t;
for(i=0;i{
t=a[i];
a[i]=a[N-1-i];
a[N-1-i]=t;
}
for(i=0;i{
printf("%d",a[i]);
}
}
voidmain()
{
inti,a[N];
printf("请输入一维数组各元素的值:
\n");
for(i=0;iscanf("%d",&a[i]);
fun(a);
printf("\n");
}
思考:
如果要对7个元素的数组进行逆置操作,只需要修改什么地方数组元素的下标可以是算术表达式吗有何要求
8-8编写程序,打印如下的杨辉三角形。
1
11
121
1331
14641
解:
#include""
#defineN6
voidmain()
{
inti,j,a[N][N]={1},k;
for(i=1;i{
for(j=1;jif(j==1||i==j)a[i][j]=a[0][0];
elsea[i][j]=a[i-1][j-1]+a[i-1][j];
}
for(i=1;i{
for(k=1;k<=N-i;k++)/*每行前面的空格*/
printf("");
for(j=1;j<=i;j++)
printf("%4d",a[i][j]);
printf("\n");
}
}
思考:
在此题中定义一个a[N][N]的方阵数组显然有些浪费(有些元素闲置,却占用存储空间),可否考虑用一维数组进行处理
8-9编写程序,用筛选法求100-1000之间的素数。
解:
#include""
#defineN1000
voidmain()
{
inti,a[N],n=0,db;
for(i=1;ia[i]=1;
for(i=2;i{
if(a[i]==0)continue;
db=i*2;
while(db{
a[db]=0;
db=db+i;
}
}
for(i=100;iif(a[i]==1)
{
printf("%d",i);
n++;
if(n%18==0)printf("\n");
}
printf("\n");
}
思考:
在程序实际已求出了什么范围之间的所有素数在while循环中的“a[db]=0;”语句的作用是什么了
8-10编写程序,利用数组实现大整数的加减运算。
假定大整数不超过10位数字。
解:
#include""
#include""
#defineN10
inta[N],b[N],c[N],d[N],jw=0;
intflag=1;/*标志两个大整数的大小关系*/
voidchag0(inta[],intn)
{
for(inti=0;i<=n;i++)
a[i]=0;
}
voidadd()/*求两个大整数的和*/
{
inti;
for(i=0;i{
c[i]=(a[i]+b[i]+jw)%10;
jw=(a[i]+b[i]+jw)/10;0”...
即第一个字母变成第26个字母,第i个字母变成第26-i+1个字母。
非字母字符不变。
编写程序将密码译回原文,并输出密码和原文。
解:
#include""
#include""
#defineN100
voidmain()
{
inti=0;
charch[N],tran[N];
printf(“请输入密码电文字符串(<100):
”);
getch(ch);
while(ch[i]!
=’\0’)
{
if(ch[i]>=’A’&&ch[i]<=’Z’)
tran[i]=(90-ch[i])+65;
elseif(ch[i]>=’a’&&ch[i]<=’z’)
tran[i]=(122-ch[i])+97;
elsetran[i]=ch[i];
i++;
}
tran[i]=’\0’;
printf(“\n电文密码:
%s”,ch);
printf(“\n原文是:
%s\n”,tran);
}
思考:
在C语言中,对字符的比较是如何进行的其基本比较规则是什么
8-18编写程序,读入若干国家的名称,按字典顺序排序输出。
解:
#include""
#include""
#defineN50
#defineM20
voidmain()
{
inti,j,n=0;
charcname[N][M],tran[N];
printf("请输入国家名称(<50个且每个名称不超过20个字符,当第一个字符为空格是结束):
\n");
for(i=0;i{
gets(cname[i]);
if(cname[i][0]=='')break;
n++;
}
for(i=0;ifor(j=i+1;jif((strmp(cname[i],cname[j]))>0)
{
strcpy(tran,cname[i]);
strcpy(cname[i],cname[j]);
strcpy(cname[j],tran);
}
printf("按字典顺序排序后为:
\n");
for(i=0;iputs(cname[i]);
}
思考:
语句“if(cname[i][0]==‘’)break;”的作用是什么若无此语句,程序运行将会出现什么状况。
8-19若A为n×n对称方阵,将A压缩存放到一维数组B中,使B具有n(n+1)/2个元素,且A中信息可全部在B中找到。
解:
#include""
#defineN5
#defineMN*(N+1)/2/*用宏处理一维数组的动态下标,内容参见第12章*/
voidmain()
{
inta[N][N],b[M],i,j,k;
printf("请输入方阵A的值:
\n");
for(i=1;i{
for(j=1;jscanf("%d",&a[i][j]);
}
for(i=1;ifor(j=1;j<=i;j++)
{
k=i*(i-1)/2+j;
b[k]=a[i][j];
}
printf("利用一维的b数组输出方阵的值:
\n");
for(i=1;i{
for(j=1;j{
if(i>=j)k=i*(i-1)/2+j;
elsek=j*(j-1)/2+i;
printf("%d",b[k]);
}
printf("\n");
}
}
思考:
如果在一个方阵中有大量的0元素(称为稀疏矩阵),如何进行一维的压缩存储
8-20某单位用现金发放工资,编写程序计算各种面值的最佳张数,
以保证发给职工工资时不需找零。
职工工资与各种面值的张数均要求用数组描述。
解:
#include""
#defineN30
voidmain()
{
inti,j;
floatsalary[N];
ints,money[10]={1000,500,200,100,50,20,10,5,2,1};
intsum[10];/*存放各种面值的张数*/
for(j=0;j<10;j++)
sum[j]=0;
printf("请输入每个职工的工资(精确到角):
\n");
for(i=0;iscanf("%f",salary+i);
for(i=0;i{
s=int(10*salary[i]);/*取出第i个工人的工资并转化为角*/
for(j=0;j<10;j++)
{
sum[j]+=s/money[j];
s=s%money[j];
}
}
/*输出结果*/
for(i=0;i<10;i++)
{
if(i<7)printf("%d元",money[i]/10);
elseprintf("%3.1f元",money[i]/;
}
printf("\n");
for(i=0;i<10;i++)
printf("%d",sum[i]);
printf("\n");
}
思考:
s/money[j],s%money[j]这两个表达式是用来求什么的如果不用角为单位,程序应如何设计
8-21编写n个学生、m门课程的成绩处理程序:
(1)实际学生人数、课程门数由键盘输入。
(2)n个学生、m门课程的成绩用二维实型数组描述,同时考虑学生姓名、学号数据。
(3)求出每个学生的总成绩、平均成绩、并按总成绩排序。
(4)求出每门课程的平均成绩和不及格的人数。
解:
#include""
#include""
#defineN100//假定学生人数不超过100
#defineM8//假定课程门数不超过8
voidmain()
{
intn,m,i,j,k,lo,t;
intno[N],sc[N][M],sum[N],csum[M],dave[M];
floatrave[N],cave[M],ave;
charname[N][10],nam[10];
printf("请输入(学生人数,课程门数):
");
scanf("%d,%d",&n,&m);
for(i=0;i{
printf("\n请输入第%d个学生的学号、姓名:
",i+1);
scanf("%d",&no[i]);gets(name[i]);
printf("各门课的考试成绩:
");
for(j=0;jscanf("%d",&sc[i][j]);
}
for(i=0;i{
sum[i]=0;
for(j=0;jsum[i]+=sc[i][j];
rave[i]=sum[i]/m;
}
for(j=0;j{
csum[j]=0;dave[j]=0;
for(i=0;i{
if(sc[i][j]<60)dave[j]++;
csum[j]+=sc[i][j];
}
cave[j]=csum[j]/n;
}
for(i=0;i{
k=i;
for(j=i+1;jif(sum[k]lo=no[i];no[i]=no[k];no[k]=lo;
strcpy(nam,name[i]);strcpy(name[i],name[k]);strcpy(name[k],nam);
t=sum[i];sum[i]=sum[k];sum[k]=t;
ave=rave[i];rave[i]=rave[k];rave[k]=ave;
for(j=0;j{
t=sc[i][j];sc[i][j]=sc[k][j];sc[k][j]=t;
}
}
/*输入显示过程*/
printf("名次学号姓名");
for(i=0;iprintf("总成绩平均成绩\n");
for(i=0;i{
printf("%2d%d%10s",i+1,no[i],name[i]);
for(j=0;jprintf("%d%7.2f\n",sum[i],rave[i]);
}
printf("\n各科平均成绩:
");
for(j=0;jprintf("\n不及格人数:
");
for(j=0;jprintf("\n");
}
思考:
二维数组是否可以看作由若干一维数组构成此题中的排序采用了什么方法
8-22在保龄球比赛中,已知每次击倒的保龄球数。
计算在一局比赛中一个人的得分,要求同时算出每一轮的得分和每一轮之后的累计得分。
保龄球比赛一局共十轮,前九轮中每一轮最多打两次球;第十轮可以大两次或三次球,每轮几分规则如下:
(1)如果一轮中第一个球击倒全部10只保龄球(称为Strike,好球),则这一轮的得分等于10分加下两次击倒保龄球的只数。
(2)如果一轮中两个球击倒全部10只保龄球(称为Spare,成功),则这一轮的得分等于10分加下一次击倒保龄球的只数。
(3)如果一轮中两个球一共击倒保龄球只数少于10个(称为Nomark,平常),则这一轮的得分等于所击倒保龄球的总只数。
解:
此题比较复杂,详细处理过程请参见本书上机实验指导部分的综合练习。
为了便于理解,在此我们先将问题简化为:
当一局十轮全部滚完后,再进行积分的显示与累计。
程序如下:
解:
#include""
voidmain()
{
inti,j,a[11][2],sc[10],sum[10];
a[10][0]=0;a[10][1]=0;a[11][0]=0;a[11][1]=0;
printf("请输入各轮两次的击倒的保龄瓶(球)数\n");
for(i=0;i<11;i++)
{
if(i<10)
{
printf("第%d轮第一次击倒瓶球数:
",i+1);
scanf("%d",&a[i][0]);
if(a[i][0]<10)
{
printf("第%d轮第二次击倒瓶球数:
",i+1);
scanf("%d",&a[i][1]);
}
else{printf("OK!
\n");a[i][1]=0;}
}
else
{
if(a[9][0]+a[9][1]<10)break;
printf("附加第一次击倒瓶球数:
");
scanf("%d",&a[i][0]);
if(a[9][0]==10)
{
printf("附加第二次击倒瓶球数:
");
scanf("%d",&a[i][1]);
}
else{printf("OK!
\n");a[i][1]=0;}
if(a[9][0]<10||a[i][0]+a[i][1]<10||a[i][0]!
=10)break;
}
}
for(i=0;i<10;i++)
{
if(a[i][0]==10)
{if(a[i+1][0]==0&&i<9)
sc[i]=a[i][0]+a[i+1][0]+a[i+2][0];
elsesc[i]=a[i][0]+a[i+1][0]+a[i+1][1];
}
elseif(a[i][0]+a[i][1]==10)
sc[i]=a[i][0]+a[i][1]+a[i+1][0];
elsesc[i]=a[i][0]+a[i][1];
if(i==0)sum[i]=sc[i];
elsesum[i]=sum[i-1]+sc[i];
}
printf("轮次:
");
for(i=1;i<=10;i++)printf("%4d",i);
printf("附加");
for(j=0;j<2;j++)
{
printf("\n第%d次得分:
",j+1);
for(i=0;i<11;i++)
if(a[i][j]!
=0||j==0||a[i][0]!
=10)printf("%4d",a[i][j]);
elseprintf("/");
}
print