2010-09-19 199 views
19

如果我嘗試的東西,如:簡單的C scanf不起作用?

int anint; 
char achar; 

printf("\nEnter any integer:"); 
scanf("%d", &anint); 
printf("\nEnter any character:"); 
scanf("%c", &achar); 
printf("\nHello\n"); 
printf("\nThe integer entered is %d\n", anint); 
printf("\nThe char entered is %c\n", achar); 

它允許輸入整數,然後跳過第二scanf徹底,這真是奇怪,因爲當我(第一char scanf函數)交換兩個,它工作正常。究竟什麼是錯的?

+1

你的指針有錯誤的大小,ANINT是這只是一個排隊值而不是字符串比較有用char和achar是一個int。不要這樣做。 – 2010-09-19 06:44:10

+0

@Variable Length Coder:對此我感到抱歉,只是解釋了一個更簡單的例子,並混合到了兩個。那個錯誤與我的問題無關,修正了這個例子。 – John 2010-09-19 06:44:48

回答

22

當讀取使用scanf輸入,輸入被讀取返回鍵被按下,但通過返回鍵生成的新行不被scanf,這意味着未來你從標準輸入讀取char時候會有一個消耗後準備閱讀的換行符。避免

一種方法是使用fgets讀取輸入的字符串,然後提取您想使用sscanf作爲什麼:

char line[MAX]; 

printf("\nEnter any integer:"); 
if(fgets(line,MAX,stdin) && sscanf(line,"%d", &anint)!=1) 
    anint=0; 

printf("\nEnter any character:"); 
if(fgets(line,MAX,stdin) && sscanf(line,"%c", &achar)!=1) 
    achar=0; 

另一種方式來消耗換行符將scanf("%c%*c",&anint);%*c將從緩衝區讀取換行符並丟棄它。

您可能需要閱讀此:

C FAQ : Why does everyone say not to use scanf?

+1

你需要'%d'格式後面的'%* c'(或者相反),不是嗎?雖然這是不可靠的 - 如果用戶在數字之後和換行符之前鍵入空格或其他內容。我認爲'fgets()'+'sscanf()'更好。 – 2010-09-19 06:47:55

+3

@Jonathan:你說得對。在'%d'之後我們需要它。是的'fgets + sscanf'總是更好。 – codaddict 2010-09-19 06:52:43

+0

@codeaddict:對於冗長的接受感到抱歉,但是您確實給了我更多的關於內部工作的深入見解。我真的很感謝C FAQ鏈接,如果我能夠更好地教新朋友這些事情是明智的以後會幫助別人。 – John 2010-09-29 01:49:38

5

它不會跳過第二個scanf();第二個scanf()讀取第一個scanf()留下的換行符。大多數格式代碼跳過白色空間; %c格式不會跳過空格。

12

其他的答案是正確的 - %c不跳過空白。讓它這樣做最簡單的方法是%c前放置空白:

scanf(" %c", &achar); 

(格式字符串中的任何空白將使scanf消耗所有連續的空格)。

+0

如何跳過空白有助於放棄換行符?例如:'scanf(「\ n%c」,&achar);'也可以。 – cpx 2012-12-15 17:29:02

+2

@cpx:因爲換行符是空格。格式字符串中的任何空格的行爲與其他任何空白字符相同,因此'\ n'與空格一樣好(但又多了一個字母)。 – caf 2012-12-15 22:29:28

0

在每次printf調用之後,還要嘗試_flushall()。 。基本上,默認情況下MS的C++緩衝流輸出,並且刷新導致輸出流爲空。

0

調用getchar()之前scanf也將清除存儲的換行符。更輕盈更態勢

char input_1; 
char input_2; 
getchar(); 
scanf("%c", &input_1); 
getchar(); 
scanf("%c", &input_2); 

將刷新換行符,在代碼的連續行,你知道