好久不见,我们学校终于要开学了。那么这个账号也开始更新起来了哈哈哈。
今天这个程序很简单,但是值得深入思考。
话不多说,先看看效果,然后上代码:
发现结果还是不错的哈?看看代码其实很简单,但后面要说的才是重点。
#include "stdio.h"
#include "stdlib.h"
int main()
{
float num1,num2,result;//定义浮点型变量作为运算的数和结果
char str;//运算符号
printf("输入你想运算的式子,以=0结尾\n");
scanf("%f%c%f",&num1,&str,&num2);//输入第一个表达式
switch(str)//用switch函数来判断运算符号,进行相应的算法
{
case '+' :
result = num1 + num2;
break;
case '-' :
result = num1 - num2;
break;
case '*' :
result = num1 * num2;
break;
case '/' :
if(num2==0)//判断除数是否为0,防止出错
{
printf("除数不能为0!\n");
result = num1;//将num1的值赋予结果,使得程序顺利进行
break;
}
result = num1 / num2;
break;
}
// system("cls");
// printf("%.2f",result);
while(str!='=')//当出现等号时停止循环
{
fflush(stdin);//清除缓冲区,防止\n使scanf扫漏数值出错
scanf("%c%f",&str,&num2);
switch(str)
{
case '+' :
result = result + num2;
break;
case '-' :
result = result - num2;
break;
case '*' :
result = result * num2;
break;
case '/' :
if(num2==0)
{
printf("除数不能为0!\n");
break;
}
result = result / num2;
break;
}
}
system("cls");//清屏
printf("最终结果为%.2f",result);//得出结果
system("pause");
return 0;
}
对于新手来说,C语言有一个函数一定经常用(看标题也知道我要说谁了吧)——“scanf”
scanf顾名思义就是扫描,目的是扫描缓冲区来获取你的键入值。比如scanf %d,那么就会扫描缓冲区中的一个整型。
似乎很合理,但是scanf有一个催命符——每次用完都会点回车键。回车相当于输入了一个\n。这是用scanf时第一个要注意的地方,因为写这个程序时,我忽略了这一点,导致结果始终都不对。原因就在这里,当我第一次用scanf后点击了回车,然而再次用scanf时会发现result再也无法赋值。
这里我通过观察返回值发现(也是个人猜测,请大佬指正)result被录入了第一次scanf留下的“\n”导致数据错误而无法进行接下来的语句,所以这里加入了fflush(stdin);有兴趣的朋友可以试着观察返回值。
所以以后用scanf发生错误时,可以试着加一句fflush(stdin);
关于scanf第二个要说的就是大名鼎鼎的vs了,vs2017删除了scanf用了scanf_s来代替。存在就有理,删除便是没有理。我们先看看scanf_s的区别:
- scanf_s() 是针对“ scanf()在读取字符串时不检查边界,可能会造成内存泄露”这个问题设计的。
- scanf_s()用于读取字符串时,必须提供一个数字以表明最多读取多少位字符,以防止溢出。
-
int scanf(const char * restrict format,...); int scanf_s(const char * restrict format,...,Number); 大概意思是 scanf("<格式化字符串>",<地址表>); scanf_s("<格式化字符串>",<地址表>,<数量>);
显而易见,scanf_s的优越性就出来了,多了一个number可以检查数量,防止程序的溢出。这在char当中最为重要!!
值得一提的是,在int中,scanf_s用法和scanf一样