java 輸入流異常處理並重新輸入,無限迴圈拋異常問題處理
最近發現了一個問題,使用Scanner輸入流時,如果做了異常處理,nextInt輸入有誤丟擲異常時,迴圈在次輸入會出現無限迴圈丟擲異常,直至棧溢位,程式崩掉。這是什麼原因呢?
Scannersc=newScanner(System.in);
booleanflag=true;
System.out.println("請輸入您需要的資訊:");
while(flag){
try{
intnumber=sc.nextInt();
}catch(Exceptione){
System.out.println("您的輸入有誤,請重新輸入");
e.printStackTrace();
}
}
通過查資料解決了這個問題,這是由於Scanner接受鍵盤輸入資訊的機制所造成的後果:
Scanner在接受鍵盤輸入時,在記憶體中會有一段專門用來接收鍵盤輸入的資訊。鍵盤資訊輸入記憶體以後與你定義的接收輸入的型別匹配,如果不匹配會丟擲異常,但是鍵盤輸入的資訊會停留在記憶體當中,當下次需要輸入時直接讀取該記憶體存在的值,繼續丟擲異常,導致無限迴圈。這種情況的解決方法有三種:
1. 在try catch塊中,異常處理時,宣告一個sc.next();這一句話的作用是讀取一次記憶體中的內容,這樣等待鍵盤輸入記憶體中的資料被清空,下一次可以輸入
Scannersc=newScanner(System.in);
booleanflag=true;
System.out.println(
while(flag){
try{
intnumber=sc.nextInt();
}catch(Exceptione){
System.out.println("您的輸入有誤,請重新輸入");
sc.next();
e.printStackTrace();
}
}}
2. 每次使用Scanner之前,new Scanner(SyStem.in);也能解決問題,但是這樣做非常的消耗效能。
while(flag){
try{
sc=newScanner(System.in);
intnumber=sc.nextInt();
break;
}catch(Exception
System.out.println("您的輸入有誤,請重新輸入");
//sc.next();
e.printStackTrace();
}
}
3. 每一個輸入都使用nextLine();接收輸入後,對接收的資料進行型別的強制轉換。型別無法轉換會丟擲異常
while(flag){
try{
Stringstr=sc.nextLine();
intnumber=Integer.parseInt(str);
break;
}catch(Exceptione){
System.out.println("您的輸入有誤,請重新輸入");
//sc.next();
e.printStackTrace();
}
}