2015-09-20 81 views
0

雖然我可以確認我正在輸入正確類型的輸入到我的C程序中,但我無法正確解釋它的條件。當我運行以下代碼時,程序成功調用lengthFormula(),然後打印"Choose from the following..."輸入提示。C程序條件無法識別可操作的輸入

int main(void) 
{ 
    char newCalculation; 

    do 
    { 
     char newCalculation; 

     lengthFormula(); 

     printf("\nChoose from the following:\n a.) Calculate the length of a multi-bar scene in this project\n b.) Calculate bar length for a NEW project\n c.) Exit\n\n"); 
     scanf(" %c", &newCalculation); 

     /* printf("%c", newCalculation); */ 

    }while(tolower(newCalculation) == 'b'); 

    if(tolower(newCalculation) == 'a') 
    { 
     float barLength; 
     multiBar(barLength); 
    } 

    if(tolower(newCalculation) == 'c') 
    { 
     exitProgram(); 
    } 
    return 0; 
} 

當我進入a,而不是再次調用lengthFormula()main()回報0和程序終止。當我取消註釋第二個printf()調用並再次編譯/運行時,輸入a返回a,但它仍然返回0 /程序終止,而不是調用lengthFormula()

在@simplicisveritatis的建議,我也試着將我的條件語句,像這樣的主要do-while循環中,具有相同的結果:

int main(void) 
{ 
char newCalculation; 

do 
{ 
    char newCalculation; 

    lengthFormula(); 

    printf("\nChoose from the following:\n a.) Calculate the length of a multi-bar scene in this project\n b.) Calculate bar length for a NEW project\n c.) Exit\n\n"); 
    scanf(" %c", &newCalculation); 

    /* printf("%c", newCalculation); */ 
if(tolower(newCalculation) == 'a') 
    { 
     float barLength; 
     multiBar(barLength); 
    } 

    if(tolower(newCalculation) == 'c') 
    { 
     exitProgram(); 
    } 

}while(tolower(newCalculation) == 'b'); 



return 0; 
} 

我如何改變我的條件,使他們識別我的輸入?請不要告訴我使用getchar(),因爲每次我這樣做,其他人都會告訴我使用scanf(),其他人說這是危險的。我只是想了解爲什麼我的條件不起作用。

+0

爲什麼他們告訴你使用'scanf()'?,請任何理由。你是否包含'stdio.h'和'ctype.h'?而這個「浮動槓」 multiBar(barLength);'是未定義的行爲,因爲你永遠不會初始化'barLength'。 –

+0

我們知道,有關於如何從用戶獲得輸入的章節。人們鄙視scanf,但其他人使用它也一樣。一些人堅持cin >> v,其他人則警告說「這會給你一個字符串」......但是,您的scanf函數在上下文中是暫時的。 – JVene

+0

'cin >> v'與這個問題無關,因爲這是[tag:c]而不是[tag:C++],並且是'scanf()'是可怕的。特別是因爲它沒有正確地在書本中出現,他們通常忽略它的返回價值。 –

回答

1

您將在循環內重新聲明newCalculation。用過的那個循環與你不一樣的是scanf() ed。

事實上,dowhile循環外,newCalculation甚至沒有初始化,所以當你把它傳遞給tolower()它可以具有任何價值,這是不可能知道哪一個原則。

取出聲明內循環,

#include <stdio.h> 
#include <ctype.h> 

int main(void) 
{ 
    char newCalculation; 
    do 
    { 
     lengthFormula(); 

     printf("\nChoose from the following:\n a.) Calculate the length of a multi-bar scene in this project\n b.) Calculate bar length for a NEW project\n c.) Exit\n\n"); 
     scanf(" %c", &newCalculation); 

     /* printf("%c", newCalculation); */ 

    } while(tolower(newCalculation) == 'b'); 

    if (tolower(newCalculation) == 'a') 
    { 
     float barLength = 0.0F /* please initialize this before calling the function */; 
     /* Or just multiBar(0.0F) */ 
     multiBar(barLength); 
    } 

    if (tolower(newCalculation) == 'c') 
    { 
     exitProgram(); 
    } 
    return 0; 
} 
+0

當我從循環中刪除聲明,然後編譯/構建,我得到錯誤 'newCalculation'未聲明(首次在此函數中使用) 它已經在循環中聲明,我可以在哪裏聲明它? 我也嘗試過在全局聲明'newCalculation',雖然編譯時沒有問題,但它將我帶回到最初的運行時問題。 –

+0

不,在'do {...'之前的第一個聲明就夠了。除了scanf()失敗以外,您不需要其他任何東西。無論如何,這種情況不太可能發生。 –

0

好了,讓我們開始字符newCalculation。在你的示例中,一次在do循環之外聲明一次,一次在do循環之內聲明它。這意味着你有兩個,while循環內部的一個不被while測試識別,這意味着tolower(newCalculation)不是「看到」你輸入的字母,它看到了在循環外部聲明的未初始化newCalculation中的垃圾。刪除內部的一個。

此外,在聲明它的位置將其初始化爲零。

你表明你有一個習慣,不用初始化你再次使用float barLength;來表示float barLength(0);或類似的東西。

也就是說,您對'a'的測試確實需要調整長度。但是,除非剪切事故堆棧在外部新計算中留下'b'或'B',否則循環不會重複。你真正打算在這裏停止一個'c'程序...這意味着你不需要函數exitProgram,只需要將這個while測試改爲類似於:

while(tolower(newCalculation) != 'c');