C语言程序设计第三次作业
1
改错题:计算f(x)的值:输入实数x,计算并输出下列分段函数f(x)的值,输出时保留1位小数。
源程序:
#include <stdio.h>
int main(void)
{
double x,y;
printf("Enter x: \n");
scanf("=%f", x);
if(x = 10);
{
y = 1 / x
}
else (x != 10)
{
y = x;
}
printf("f(%.2f) = %.lf\n" x y);
return 0;
}
错误信息:
错误原因及改正:"y = 1 / x"后没有加";"构成完整语句,应在后面加上";"使之构成完整语句即可。
错误信息:
错误原因及改正:if后加了";"构成一个语句使之后的"else"没有配对的"if",把if语句中的";"删去即可。
错误信息:
错误原因及改正:else后面不能跟条件,除了"x=10"之外就是"x!=10",直接用else 即可,把else后的条件删去即可。
错误信息:
错误原因及改正:引号外没有加","未把格式输出串与输出表列分开,加上","即可。
错误信息:
错误原因及改正:未在x y间加","把两个变量分开,在x后加","即可。
错误信息:
错误原因及改正:要求保留一位小数,把"%.2f"改为"%.1f"即可。
错误信息:
错误原因及改正:要求保留一位小数,把"%.lf"改为"%.1f"即可。
错误信息:
错误原因及改正:用了赋值符号而没有用等号,应把"="改为"=="即可。
改错后进行运算发现出现了如下错误:
经检查发现错误如下:
错误信息:
错误原因及改正:引号内不能有"=",应把"="删去,此外,因为定义的x是double型,所以应把"%f"改为"%.lf"才正确。
错误信息:
错误原因及改正:地址表列处x未取地址符"&",应该在"x"前加"&"--"&x"即可。
全部改正后带入几组数据进行运行计算如图:
运行结果都与预期结果相符,但同时发现输出格式与题目要求不符,做出如图对比:
此时发现应把其中的"\n"删去才与格式相符,此时运行全部正确,改错完毕。源代码如图
#include <stdio.h>
int main(void)
{
double x,y;
printf("Enter x: \n");
scanf("%lf", &x);
if(x == 10)
{
y = 1 / x;
}
else
{
y = x;
}
printf("f(%.1f) = %.1f\n" ,x ,y);
return 0;
}
2
学习总结
1.if(a)if(b) x=x+1;else y=y+1; 的确切含义是什么?这个else应该和哪个if配对?如何明确表达这种配对方法?将该段代码按照规范化的格式进行书写。
所给的代码段"if(a)if(b) x=x+1;else y=y+1"应表示在满足a和b的条件下x=x+1,否则执行"else"后的语句,为"且"的条件,用"&&"表示,而根据else与最近的未配对if配对原则,else应与第二个if配对,同时为了保证运算中if条件句不出现错误,应在每个if句处用"{}"包含语句,所以改正后的代码段应如下所示:
if(a&&b)
{
x=x+1;
}
else
{
y=y+1;
}
2.2.C语言的表达式 (-10< x <10)能够表达x在区间(-10,10)吗?为什么?如果不能,正确的表达式应该怎么写?
首先,C语言的表达式 (-10< x <10)是不能表达x在区间(-10,10)的,因为对于所给格式,系统进行运算按照从左到右的顺序进行,同时在系统内部进行判断而不是表示区间,所以输出值只能是0或1,根据先后顺序,先判断-10<x,此时有两种情况:x是大于-10小于10的数,此时判断结果为1,再与10进行比较结果还是为1,此时内部运算没有错误但还是不能表示区间,第二种情况;x是大于10的数此时先判断-10<x结果为1,由于此时x>10再进行判断时结果应为x>10,但由于前面判断结果为1,由1与10进行判断,导致结果还是1,与x本身是大于10的数情况不符,同时也不能表达区间的形式,所以如上两种情况都不能表达区间的形式。也就是说,只要输入的值大于-10,判断结果都为1,可能出现与真实情况不符的情况。正确表达区间的形式如下:
(x>-10 && x<10)
3.(1)C语言中输入数据时,如果遇到非法字符,则认为输入结束。运行程序(1),输入123a,看看输出结果是什么?你能解释是为什么吗?,
程序(1)
#include <stdio.h>
int main()
{
int a, b;
scanf("%d %d", &a, &b);
printf("a = %d, b = %d\n", a, b);
return 0;
}
输入下列程序得到如图:
可以看到在a之前输入停止,a被赋值123,而b则被赋值为没有输入的一个数字1,这是由于输入过程中如果遇到非法字符则会停止输入。在a后继续输入数字如图
想要让a正确输入,经过查询得知,应该用适用于单个字符输出的%c代替b处的%d,如图
此时输入123a,a在"a"之前停止输入,值为123,a则被赋值给b,得到b=a如图
因为此时b已被定义为字符型,此时若输入数字则会出现与上面一样的问题,数字会被认为时非法字符,输入数字则会停止输入。做如下图试验
结果与预期猜想一致,数字被当作非法字符而停止输入,从而说明输入遇到非法字符停止输入的问题。
(2)scanf()函数的返回值是成功读入数据的个数,如果没有读取任何数据,则返回0。运行程序(2),分别输入123 45和123a,看看输出结果是什么?为什么?
程序(2)
#include <stdio.h>
int main()
{
int a, b,n;
n = scanf("%d %d", &a, &b);
printf("n = %d\n", n);
return 0;
}
输入123和45结果如图:
根据题知scanf()函数的返回值是成功读入数据的个数,此处返回值为2,表示成功读入两个数据。
而输入123a得到如下图结果:
此时因为第一组数据有非法字符"a",导致输入被终止,所以成功导入的数据个数为1,因此输出为"n = 1"。
修改程序(1),当输入非法数据时,输出“Input error!".
由于第一组数据为123和45,第二组数据为123a,由程序(2)可以想到他们的scanf()返回值分别为1和2,由此可想到设另一个变量n来表示输入了非法字符与正确数据,程序如下图
#include <stdio.h>
int main()
{
int a, b,n;
scanf("%d %d", &a, &b);
if(a == 2)
{
printf("a = %d, b = %d\n", a, b);
}
else
{
printf("Input error!");
}
return 0;
}
此时分别输入数据123 45和123a,得到如下图:
都与预期结果相符。
4.小结:(1)注意字符常量和字符串常量的区别:字符常量是用单引号括起来的单个普通字符或转义字符,而字符串常量十用双引号括起来的字符序列,可包括多个字符。同时要注意不要把字符串赋给字符变量。字符变量输入输出时用"%c"表示。(2)字符常量值:该字符的ASCII码值。定义字符型变量用char来定义,包括0-255之间的整数。同时要记住char和int之间也可以进行运算。(3)如果强行结束一条语句可用"exit(0);"表示,此时要在前面加一个库文件 #include <stdlib.h>。(4)一些字符常量值和意义:'A'-65,'a'-97,'0'-48,'\n'-10,\n-换行,\a-响铃,\t-水平制表,'-单引号,"-双引号,\-反斜线。(5)字符输入输出函数:getchar,putchar.随即函数:rand()(在<stdlib.h>中定义)。系统时间:(<time.h>)
3 实验总结
1.计算分段函数
流程图:
源代码:
#include <stdio.h>
#include <math.h>
int main(void)
{
double x,f;
scanf("%lf",&x);
if(x >= 0)
{
f = sqrt(x);
}
if(x < 0)
{
f = pow(x + 1,2) + 2 * x + 1 / x;
}
printf("f(%.2f) = %.2f",x,f);
return 0;
}
测试数据及运行结果:
输入10得到结果如图,与预期相符
输入-0.5得到如图:
本题涉及到调用函数以及函数的使用,以及简单的选择结构,并没有出现问题。
2.算术入门之加减乘除
流程图:
源代码:
#include<stdio.h>
int main( )
{
int m,n;
scanf("%d %d",&m,&n);
printf("%d + %d = %d\n",m,n,m+n);
printf("%d - %d = %d\n",m,n,m-n);
printf("%d * %d = %d\n",m,n,m*n);
if(m % n == 0)
{
printf("%d / %d = %d\n",m,n,m/n);
}
else
{
printf("%d / %d = %.2f\n",m,n,(double)m/n);
}
return 0;
}
测试数据及运行结果:
测试结果均与预期相符。
问题:如下图:
原因:因开始运行时没注意定义的a b时整形变量,在输出时没有把结果定义成浮点型,导致结果错误。
解决方法:在"m/n"前加上"(double)"使结果变成浮点型。除此之外是较为简单的选择结构,并未出现问题。
3.输出三角形面积和周长
流程图:
源代码:
#include <stdio.h>
#include <math.h>
int main(void)
{
int a,b,c;
double s,aera,perimeter;
scanf("%d%d%d",&a,&b,&c);
if((a + b > c) && (a + c > b) && (b + c > a))
{
s = ((double)a + b + c) / 2.0;
aera = sqrt(s * (s - a) * (s - b) * (s - c));
perimeter = a + b + c;
printf("area = %.2f; perimeter = %.2f",aera,perimeter);
}
else
{
printf("These sides do not correspond to a valid triangle");
}
return 0;
}
测试数据及运行结果:
都与预期结果相符。
由于上题对输出结果的浮点型有了一定了解与记忆,所以本题并未出现问题,但做题为了避免出现与上题一样的错误,定义的整形变量在输出时要求浮点型,所以改为a + b + c / 2.0可以避免出现问题,更方便计算。
4.出租车计价
流程图:
源程序:
#include <stdio.h>
int main(void)
{
double longth,m1,m3;
int time,m2;
scanf("%lf%d",&longth,&time);
if (longth <= 3)
{
m1 = 10;
}
else if(longth > 3 && longth <= 10)
{
m1 = 10 + 2 * (longth - 3);
}
if(longth > 10 && time < 5)
{
m1 = 10 + (longth - 3) * 2 + (longth - 10) + m2;
}
if(longth > 10 && time >= 5)
{
m1 = 10 + (longth - 3) * 2 + (longth - 10) + m2;
}
if (time >= 5)
{
m2 = (time / 5)* 2;
}
else
{
m2 = 0;
}
m3 = m1 + m2;
printf("%.0f\n",m3);
return 0;
}
测试数据及运行结果:
问题1:计算结果出现错误由于对超出十公里后的收费和空车费理解错误导致计算结果错误
解决方法: m1 = 10 + (longth - 3) * 2 + (longth - 10) + m2×3;改为 m1 = 10 + (longth - 3) * 2 + (longth - 10) + m2;
问题2:对于四舍五入的表达方法出现错误
解决方法:应该用"%.0f"来表示保留0位小数,也就是四舍五入。
4 PTA提交列表
以上是我本次博客园作业,希望老师和同学给予意见和建议。