2017-10-13 3 views
0

Ich bin ein Student in einem Intro C++ Informatikkurs, und dies ist das erste Mal, dass ich hier gepostet habe. Wir haben gerade etwas über while-Schleifen gelernt, und obwohl die Zuweisung es nicht erfordert, versuche ich, die Eingabeüberprüfung für diese Aufgabe durchzuführen. Das Programm soll eine Liste von Zahlen lesen und die Positionen in der Liste herausfinden, wo sich die erste und die letzte 8 befinden. Wenn ich also eine Liste von vier Zahlen (1, 8, 42, 8) habe, dann sind die ersten und letzten 8 Positionen 2 und 4. Die Größe des Satzes wird vom Benutzer bestimmt.C++ Eingabe Validierung während Schleife nicht beendet

Ich habe versucht, eine while-Schleife zu erstellen, die getestet wurde, um sicher zu sein, dass das, was der Benutzer eingegeben hat, tatsächlich eine Ziffer war, aber wenn ich versuche, etwas einzugeben wie "." oder "a" geht die Schleife unendlich weiter und endet nicht. Ich kann meinen Fehler nicht finden, und soweit ich das beurteilen kann, verwende ich genau die gleiche Syntax wie in meinem Lehrbuch. Kann mir jemand zeigen, was mit meiner While-Schleife nicht stimmt?

int numbers,   //How large the set will be 
    num,    //What the user enters for each number 
    first8position = 0, //The first position in the set that has an 8 
    last8position = 0; //The last position in the set that has an 8 

//Prompt the user to get set size 
cout << "How many numbers will be entered? "; 
cin >> numbers; 

//Loop to get all the numbers of the set and figure out 
//which position the first and last 8 are in 
for (int position = 1; position <= numbers; position++) 
{ 
    cout << "Enter num: "; 
    cin >> num; 

    //If num isn't a digit, prompt the user to enter a digit 
    while (!isdigit(num)) 
    { 
     cout << "Please enter a decimal number: "; 
     cin >> num; 
    } 

    //If num is 8, and first8position still isn't filled, 
    //set first8position to the current position. 
    //Otherwise, set last8position to the current position. 
    if (num == 8) 
    { 
     if (first8position == 0) 
      first8position = position; 
     else 
      last8position = position; 
    } 


} 

//If the set had an 8, print what its position was 
if (first8position != 0) 
    cout << "The first 8 was in position " << first8position << endl; 

//If there was more than one 8, print the last 8 position. 
//Otherwise, the first and last 8 position are the same. 
if (last8position != 0) 
    cout << "The last 8 was in position " << last8position << endl; 
else 
    cout << "The last 8 was in position " << first8position << endl; 

//If there were no 8s, say so. 
if (first8position == 0) 
    cout << "Sorry, no eights were entered."; 

return 0; 

}

+3

verwandt/Betrogene https://stackoverflow.com/questions/19521320/why-do-i-get-an-infinite-loop-if-i-enter-a-letter-rather-than-a -number – NathanOliver

+4

Sie verwenden auch 'std :: isdigit' nicht korrekt. Um zu sehen, wie es funktioniert, siehe: http://en.cppreference.com/w/cpp/string/byte/isdigit – NathanOliver

Antwort

1

Zwei Fragen zu Ihren Endlosschleife führen:

Zuerst mit cin >> num, versuchen Sie in einem integrierten Wert zu lesen. Wenn ein Benutzer so etwas wie a oder . eingibt, was nicht der Beginn eines ganzzahligen Wertes sein kann, wird nichts eingelesen und die a oder . verbleiben im Eingangspuffer; Daher wird jedes folgende cin >> num sofort fehlschlagen (ohne dem Benutzer die Möglichkeit zu geben, etwas einzugeben, da die a oder . noch im Eingabepuffer sind und dort bleiben werden). In einem solchen Fall müssen Sie diese Zeichen aus cin, z. Mit , und Sie müssen die failbit zurücksetzen, die in diesem Fall auch eingestellt ist.

Zweitens beachten Sie, dass isdigit(int c) prüft, ob die ASCII -Wertes c ist eine Ziffer, das heißt, wenn c >= 48 && c <= 57. Ihr Scheck isdigit(num) schlägt daher fehl, bis ein Benutzer eine Nummer zwischen 48 und 57 eingibt.

Siehe den folgenden Code, der den Umgang mit Eingabefehlern veranschaulicht. Ich hoffe es hilft.

int main() { 

    int num; 
    cin >> num; 
    while (!cin.eof() && cin.fail()) { // failure when extracting an integral value? 
     cout << "not an integral value." << endl; 

     // clear failbit 
     cin.clear(); 

     // remove characters that are still in the input buffer (until next end of line) 
     cin.ignore(std::numeric_limits<std::streamsize>::max(), '\n'); 

     // next try to read in an integer 
     cin >> num; 
    } 
    if (!cin.eof()) { 
     cout << "juu:" << num << endl; 
    } 
} 
+0

Sie könnten die nächste 'num' lesen und gleichzeitig mit' while (! (Cin >> num)) '. – WorldSEnder

+0

@WorldSEnder: es müsste 'while (! (Cin >> num))' sein, aber dann können Sie in eine Endlosschleife laufen, wenn EOF erreicht ist. Dies kann durch gezieltes Testen von Failbit vermieden werden. –

+0

Ihre Antwort war klar und gründlich. Danke vielmals! – Kronimiciad

Verwandte Themen