為何int類型的變量在不小心輸入字元型之後會造成死循環
在做一個C++小項目時遇到的這個問題,如果輸入的不是整型,而是字元型資料的話,則會跳過cin >> sex;并過不了if判斷一直死循環輸出"輸入有誤,請重新輸入"
cout << "請輸入性别:" << endl;
cout << "1 --- 男" << endl;
cout << "2 --- 女" << endl;
int sex = 0;
while (true)//用這個循環,直到輸入正确為止,才會退出循環
{
//如果輸入的是1或者2,為正确值,将退出循環
//如果不是則表明輸入錯誤,則需要重新輸入
cin >> sex;
//---------------如果這裡sex輸入了+或者字元符号,會進入死循環。-------
if (sex == 1 || sex == 2)
{
abs->personArray[abs->m_Size].m_Sex = sex;
break;
}
else
cout << "輸入有誤,請重新輸入 " << endl;
}
這裡涉及到一個流狀态的概念
cin或cout 對象包含一個描述流狀态(stream state)的資料成員(從ios_base 類那裡繼承的)。流狀态(被定義為iostate類型,而iostate是一種bitmask類型)由3個ios _base 元素組成: eofbit. badbit 或failbit, 其中每個元素都是一位,可以是1 (設定)或0(清除)。當cin操作到
達檔案末尾時,它将設定eofbit:當cin操作來能讀取到預期的字元時(像前一個例子那樣),它将設定failbit. I/O失敗(如試圖讀取不可通路的檔案或試圖寫入寫保護的磁盤),也可能将failbit設定為1.在一些無法診斷的失敗破壞流時,badbit 元素将被設定(實作沒有必要就哪
些情況下設定failbit,哪些情況下設定badbit達成一緻)。當全部3個狀态位都設定為0時,說明一切順利。程式可以檢查流狀态,并使用這種資訊來決定下一步做什麼。
可以采取clear()和setstate()這兩種方法。
clear();
調用這個函數将使用預設參數0,并将清楚全部的三個狀态位(eofbit、badbit、failbit)
而調用clear(eofbit);時
将狀态設定為efobit,也就是說efobit将被設定,另外兩個狀态位将被清除。
而setstate()方法隻影響其參數中已設定的位。是以,下面的調用将設定eofbit,而不會影響其他位。
setstate(eofbit);
最後的解決方法就是在while循環中加入一個cin.clear(),然後就沒報錯了。這是我目前能想到的方法,可能還有不妥之處,可以評論交流一下。
while (true)//用這個循環,直到輸入正确為止,才會退出循環
{
//如果輸入的是1或者2,為正确值,将退出循環
//如果不是則表明輸入錯誤,則需要重新輸入
cin.clear();//加入這行就不會死循環了
cin >> sex;
if (sex == 1 || sex == 2)
{
abs->personArray[abs->m_Size].m_Sex = sex;
break;
}
else
cout << "輸入有誤,請重新輸入 " << endl;
}