Archiv verlassen und diese Seite im Standarddesign anzeigen : Tastaturpuffer/Keyboard buffer leeren
Hallo,
wie kann ich den Tastaturpuffer leeren? Ich habe in meinem Programm eine Fehlerprüfung auf falsche Eingaben. Leider funktioniert die Abfrage nicht, da sich nach der ersten fehlerhaften Eingabe das Programm in eine Endlosschleife begibt. Und zwar deswegen, weil der Tastaturpuffer immernoch gefüllt ist und die Abfrage somit immer == 0 ist (fehlerhafte Eingabe).
Ich habe es schon mit tcflush(fileno(stdin), TCIFLUSH) probiert. Leider ohne Erfolg.
Was kann ich noch probieren?
Hier mal noch meine Eingabe Funktion:
float eingabe()
{
float input;
input=0.0;
while( scanf("%f",&input) == 0 )
{
printf("Falsche Eingabe!\nBitte um erneute Eingabe: ");
tcflush( fileno(stdin), TCIFLUSH );
}
return input;
}
Ich hoffe ihr könnt mir da ein paar Tipps auf den Weg geben.
locus vivendi
27-10-2006, 23:54
Ich glaube du verwechselst Buffering des Betriebssystems mit dem Zustand des Streams als Mittel der Programmiersprache. Wenn in deinem Beispiel der Benutzer etwas inkorrekt formatiert eingibt, dann geht der Stream in einen Fehlerzustand über. Bevor du mit dem Stream weiterarbeiten kannst, musst du dich erstmal mit dem Fehlerzustand auseinandersetzen. Ich poste mal Beispielcode wie das gelöst werden könnte.
float in;
while(!(std::cin >> in) )
{
if(std::cin.fail() && !std::cin.bad() )
{
std::cout << "Falsche eingabe.\n";
std::cin.clear();
std::cin.ignore(std::numeric_limits<int>::max(), '\n');
}
else
{
// Stream ist vermutlich in einem ungünstigen Zustand.
// Muss auch irgendwie behandelt werden.
}
}
std::cout << "in = " << in;
Bitte selber die korrekten Header benutzen. Wenn dir nicht klar ist, was in dem Snippet passiert, bitte mit Hilfe einer Referenz nachvollziehen.
Danke für deine Antwort. Ich hätte wohl besser erwähnen sollen, dass der Code ausschließlich C Code beinhalten muss. Trotzdem danke! Parallel werde ich den Code ausprobieren. Für das eigentliche Programm benötige ich aber reinen C Code.
In der Funktion überprüfe ich lediglich ob scanf mir ein Ok gibt, dass eine (der Formatierung) korrekte Eingabe erfolgte. Bei falscher Eingabe sollte scanf mir erneut eine Eingabe des Wertes anbieten. Tut es aber nicht! Stattdessen verläuft sich die Schleife. Meines Wissens nach (ok ich bin erst Anfänger - von daher ist die Wahrscheinlichkeit groß das ich mich täusche) liegt das daran, dass der Buffer nicht leer ist und scanf den vorhanden Buffer nimmt, anstatt eine neue Eingabe anzufordern.
sticky bit
28-10-2006, 03:38
probiers mal mit fflush(stdin). Kann jetzt aber auch ne Niete sein, bin mir grad nicht sicher...
Dies funktioniert leider nur unter Windows Systemen :rolleyes:
locus vivendi
28-10-2006, 10:47
Ich hätte wohl besser erwähnen sollen, dass der Code ausschließlich C Code beinhalten muss.
Schade! Mit C Stdio kenn ich mich nicht so aus, und ich würde auch nicht dazu raten. Aber vielleicht kommst du weiter wenn du dir mal die Funktion "clearerr" aus <stdio.h> anschaust. Für das "ignore" aus meinem Snippet kenn ich gerade kein C-Äquivalent, aber "fgetc" sollte es auch tun.
Meines Wissens nach [...] liegt das daran, dass der Buffer nicht leer ist und scanf den vorhanden Buffer nimmt, anstatt eine neue Eingabe anzufordern.
Das denke ich auch, aber wie gesagt der C Stdio-Buffer, nicht der Betriebssystem-Buffer.
Du solltest übrignes nicht nur überprüfen ob scanf 0 zurückgibt, sondern auch auf EOF überprüfen.
sticky bit:
probiers mal mit fflush(stdin). Kann jetzt aber auch ne Niete sein, bin mir grad nicht sicher...
Das geht in der Tat nicht: Fflush kümmert sich nur um Ausgabestreams. Wenn unter Windows ein fflush dafür geeignet ist, würde das Windows fflush übrigens nicht Posix-konform sein, denn Posix schreibt ausdrücklich vor das in diesem Fall ein Fehler gemeldet werden soll. Das ist zumindest mein Verständnis des Standards, die Beschreibung ist da nicht so 100%-ig eindeutig.
sticky bit
28-10-2006, 20:04
Naja OK, war ne Niete, kommt vor... ;)
Wenn das mit locus vivendis Vorschlag mit clearerr() nicht hinhaut, dann könntest du alternativ versuchen erst mal alles in einen Puffer mit getc() oder gets() einzulesen und das dann mittels sscanf() aus dem Puffer in deine Variable schieben...
Dr.Online
28-10-2006, 20:52
Also ich hatte ein ähnliches Problem und es (da ich nicht so wirklich bewandert in C bin) gelöst, in dem ich mir eine kleine Hilfsfunktion dazugenommen hab:
void key_delete(void)
{
char trash[80];
fgets(trash, 80, stdin);
}
Die dann einfach in deiner Schleife aufrufen und es tut (glaube ich) das was es soll.
Danke! Das ist eine einfache aber trotzdem sehr gute Lösung finde ich. Da hätte ich aber auch selbst drauf kommen können :rolleyes:
Funktioniert wunderbar!!!:)
guardian
30-10-2006, 09:51
Ein einfaches
int c;
while( ( c = getchar() ) != EOF && c != '\n' );
würde es mit Sicherheit auch tun :)
Würde es im Normalfall auch tun. Nur müsste ich dann im weiteren Verlauf eine seperate Fehleingabenüberprüfung durchführen. In meinem Fall übernimmt dies bereits scanf für mich. Natürlich ist dies nur eine sehr lasche Überprüfung, aber immerhin schnell und einfach zu realisieren und für diesen Fall vollkommen ausreichend. Hoffe ich mal :cool:
Powered by vBulletin® Version 4.2.5 Copyright ©2025 Adduco Digital e.K. und vBulletin Solutions, Inc. Alle Rechte vorbehalten.