#include <stdio.h> char get_choice(void); int check_first_input (void); int check_second_input (void); float add(void); float subtract(void); float multiply(void); float divide(void); int main(void) { char choice; while ((choice = get_choice()) != 'q') { switch(choice) { case 'a': add(); break; case 's': subtract(); break; case 'm': multiply(); break; case 'd': divide(); break; default :printf("please enter the right word.\n");continue; } } printf("done!"); return 0; } char get_choice(void) { char choice; printf("Enter the operation of your choice: \n"); printf("a. add s. subtract \n"); printf("m. multiply d. divide\n"); printf("q. quit\n"); choice = getchar(); while(getchar() !='\n') continue; return choice; } float add(void) { float first_number,second_number; float result; first_number = check_first_input(); second_number = check_second_input(); result = first_number + second_number; printf("%.1f + %.1f = %.1f\n",first_number,second_number,result); return result; } float subtract(void) { float first_number,second_number; float result; first_number = check_first_input(); second_number = check_second_input(); result = first_number - second_number; printf("%.1f - %.1f = %.1f\n",first_number,second_number,result); return result; } float multiply(void) { float first_number,second_number; float result; first_number = check_first_input(); second_number = check_second_input(); result = first_number * second_number; printf("%.1f * %.1f = %.1f\n",first_number,second_number,result); return result; } float divide(void) { float first_number,second_number; float result; first_number = check_first_input(); second_number = check_second_input(); while (second_number == 0) { printf("enter a number other than 0: "); second_number = check_second_input(); } result = first_number / second_number; printf("%.1f / %.1f = %.1f\n",first_number,second_number,result); return result; } int check_first_input (void) { int input; printf("please enter the first number: "); while ((scanf("%d",&input)) == 0) { printf("%s is not an number.\n",input); printf("please enter a number,such as 2.5,-1.78E8,or 3:1"); scanf("%d",&input); } return input; } int check_second_input (void) { int input; printf("please enter the second number: "); while ((scanf("%d",&input)) == 0) { printf("%s is not an number.",input); printf("please enter a number,such as 2.5,-1.78E8,or 3"); scanf("%d",&input); } return input; }
在输入都为数字时候程序可以执行相应的操作,但是有两个问题: 1. 当输入为字母的时候会出错, 2. 在一次输入计算完毕后 在输入时候菜单栏会显示两次 如图:
第一个错误:没有搞懂 函数scanf ,我的想法是scanf(“%d”,choice)当choice输入的不是整数型时候,利用printf的%s来输出字母,这里出错了,对于%d输入的scanf 如果输入的是字符比如a 时候,scanf()将会停在那里,并把a放回输入中,不会把值赋给指定的变量。这样在程序后面如果有%c的字符输入语句将先读取字母a,但是如果程序中只有%d形式的转换说明,则scanf就一直无法越过a读取下一个字符。
修改:
在scanf(“%d”,input)不成功时,利用getchar()来输出非数字字符,这里的getchar()获得是上次input的值,并不是再从键盘获取的值。
第二个:错误出现在于scanf与getchar混用时候的错误,如图在输入22【enter】 1【enter】时候,后面的那个enter 这个换行符留在了输入队列中,而下一次的重新输入m时遇到的是getchar()函数,这就使得getchar()函数先获取【enter】的字符‘\n’,这样就不符合输入出现提示再次重新输入。 那么问题来了 为什么两次获取数字 first_number second_number 都使用了scanf(“%d”),那么为什么前一次获取first_number的操作不会影响到下一次的 seond_number的操作呢? 因为scanf函数在转换格式使用%d 的时候 会自动筛掉回车和空格 , 也就是说 上一次的sanf所留下来的回车字符对下一个sanf没有影响。但是第二次的scanf的回车遇到的是getchar()(如果遇到%c的scanf也一样)这就有影响了。
修改:
在scanf后面的加上 while(getchar() !='\n') continue;
我之前想法是这边的不等于改成等于,但是一旦这样修改那么Enter将会进入while, 那么这个enter键将被使用而不会将输入送入缓存区,这样表现出的就是第二次输入后无法进入程序,如图:
其实这个while的作用并不是为了检测到Enter键的时候进入while(这样就会导致输入无法进入缓存区),而是利用getchar()这个函数将在输入队列中的【Enter】提取出来,这样下一个get_choice中的getchar()函数就不会提取到上一次输入的【Enter】。
修改后的代码:
#include <stdio.h> char get_choice(void); int check_first_input (void); int check_second_input (void); float add(void); float subtract(void); float multiply(void); float divide(void); int main(void) { char choice; while ((choice = get_choice()) != 'q') { switch(choice) { case 'a': add(); break; case 's': subtract(); break; case 'm': multiply(); break; case 'd': divide(); break; default :printf("please enter the right word.\n");continue; } } printf("done!"); return 0; } char get_choice(void) { char choice; printf("Enter the operation of your choice: \n"); printf("a. add s. subtract \n"); printf("m. multiply d. divide\n"); printf("q. quit\n"); choice = getchar(); while(getchar() !='\n') continue; return choice; } float add(void) { float first_number,second_number; float result; first_number = check_first_input(); second_number = check_second_input(); result = first_number + second_number; printf("%.1f + %.1f = %.1f\n",first_number,second_number,result); return result; } float subtract(void) { float first_number,second_number; float result; first_number = check_first_input(); second_number = check_second_input(); result = first_number - second_number; printf("%.1f - %.1f = %.1f\n",first_number,second_number,result); return result; } float multiply(void) { float first_number,second_number; float result; first_number = check_first_input(); second_number = check_second_input(); result = first_number * second_number; printf("%.1f * %.1f = %.1f\n",first_number,second_number,result); return result; } float divide(void) { float first_number,second_number; float result; first_number = check_first_input(); second_number = check_second_input(); while (second_number == 0) { printf("enter a number other than 0: "); second_number = check_second_input(); } result = first_number / second_number; printf("%.1f / %.1f = %.1f\n",first_number,second_number,result); return result; } int check_first_input (void) { int input; char ch; printf("please enter the first number: "); while ((scanf("%d",&input)) == 0) { while ((ch = getchar()) != '\n') //这里的getchar()获得是上次input的值,并不是再从键盘获取新的值 putchar(ch); printf(" is not an number.\n"); printf("please enter a number,such as 2.5,-1.78E8,or 3 : "); } while(getchar() !='\n') //我之前想法是这边的不等于改成等于,但是一旦这样修改那么Enter将会进入while continue; // 那么这个enter键将被使用而不会将输入送入缓存区。 return input; } int check_second_input (void) { int input; char ch; printf("please enter the second number: "); while ((scanf("%d",&input)) == 0) { while ((ch = getchar()) != '\n') putchar(ch); printf(" is not an number."); printf("please enter a number,such as 2.5,-1.78E8,or 3 :"); } while(getchar() !='\n') continue; return input; }