Komisches Verhalten mit Scanner#nextFloat
Ausführen der Folgendes in Eclipse zunächst verursacht Scanner nicht erkennen, Wagenrücklauf in der Konsole effektiv blockiert weitere Eingaben:
price = sc.nextFloat();
Fügen Sie diese Zeile vor dem code bewirkt, dass der Scanner zu akzeptieren 0,23 (französische Schreibweise) als float:
Locale.setDefault(Locale.US);
Dies ist wahrscheinlich aufgrund des regionalen Einstellungen in Windows XP Pro (Französisch/Belgisch). Wenn der code erneut ausgeführt 0,23 wird noch immer akzeptiert und die Eingabe 0.23 bewirkt, dass es zu werfen java.util.InputMismatchException
.
Jede Erklärung, warum dies passiert ist? Auch gibt es einen workaround oder sollte ich einfach verwenden Float#parseFloat
?
Edit: Das zeigt, wie sich der Scanner verhält sich mit verschiedenen Gebietsschemata (kommentieren Sie die Zeilen am Anfang).
import java.util.Locale;
import java.util.Scanner;
public class NexFloatTest {
public static void main(String[] args) {
//Locale.setDefault(Locale.US);
//Locale.setDefault(Locale.FRANCE);
//Gives fr_BE on this system
System.out.println(Locale.getDefault());
float price;
String uSDecimal = "0.23";
String frenchDecimal = "0,23";
Scanner sc = new Scanner(uSDecimal);
try{
price = sc.nextFloat();
System.out.println(price);
} catch (java.util.InputMismatchException e){
e.printStackTrace();
}
try{
sc = new Scanner(frenchDecimal);
price = sc.nextFloat();
System.out.println(price);
} catch (java.util.InputMismatchException e){
e.printStackTrace();
}
System.out.println("Switching Scanner to System.in");
try{
sc = new Scanner(System.in);
System.out.println("Enter a float value");
price = sc.nextFloat();
System.out.println(price);
} catch (java.util.InputMismatchException e){
e.printStackTrace();
}
System.out.print("Enter title:");
String title = sc.nextLine(); //This line is skipped
System.out.print(title);
}
}
Edit: Diese reproduziert das Problem, wo der Scanner wartet auf einen float-Wert, kann Sie aber nicht auslösen, wenn Sie drücken Sie die EINGABETASTE:
import java.util.Scanner;
public class IgnoreCRTest {
public static void main(String[] args) {
Scanner sc = new Scanner(System.in);
System.out.println("Enter a float value:");
//On french Locale use , as the decimal separator
float testFloat = sc.nextFloat();
System.out.println(testFloat);
//sc.skip("\n"); //This doesn't solve the issue
sc.nextLine();
System.out.println("Enter an integer value:");
int testInt = sc.nextInt();
System.out.println(testInt);
//Will either block or skip here
System.out.println("Enter a string value :");
String testString = sc.nextLine();
System.out.println(testString);
}
}
Sicher. Ich ' ll fügen Sie einige code, der in ein paar Minuten Zeit.
InformationsquelleAutor James P. | 2011-01-16
Du musst angemeldet sein, um einen Kommentar abzugeben.
Ich Frage mich, wenn Sie nicht im Umgang mit einem end-of-line-token entsprechend. Oft, wenn Sie verwenden, Scanner#next###() (außer für nextLine -), und Sie erreichen einen end-of-line-token als wenn der Benutzer die EINGABETASTE drückt, wenn Sie nicht behandeln, das Ende der Zeile von token, es wird verhindert, dass der Scanner-Objekt aus entsprechend zu arbeiten. Um dieses Problem zu lösen, rufen Sie Scanner#nextLine - () wenn dieses token verarbeitet werden muss. Wenn Sie post von Ihrem code können wir sehen, ob das tatsächlich dein problem, und wenn mein Vorschlag eine Lösung bietet.
edit: nope, bist du nicht mit System.so das ist nicht das problem. Auf der anderen Seite, benötigen Sie, um die locale des Scanners vor der Annahme der französischen Nummer. d.h.,
Danke für die Antwort, aber sorry, ich habe irgendwie verpasst, dass. Wo kann er behaupten, dass die Standard-locale ist Französisch?
Danke. Festlegen der Locale-Einstellung für den Scanner funktioniert der trick (den ich verwenden wollte UNS dezimal). Irgendwelche Ideen auf, was verursacht die nextLine-übersprungen werden, die in den geänderten code? Auch, da die Locale eingestellt war ich nicht in der Lage gewesen, das problem zu reproduzieren, wo der Scanner scheint auch akzeptiert zu werden text, aber ist nicht zu erkennen, Wagenrückläufe.
seine in einem Kommentar über seine println(Locale.getDefault())
wenn Sie anrufen sc.nextFloat() nicht entfernt den Zeilenumbruch aus dem Puffer, so dass Ihre nächste Aufruf von sc.nextLine - () ist die Rückgabe eine leere Zeile (wie @hovercraft erklärt - +1!) Die Lösung ist, rufen Sie sc.nextLine - () direkt nach sc.nextFloat() und ignorieren die Ausgabe
InformationsquelleAutor Hovercraft Full Of Eels