簡體   English   中英

意外的字符串流行為

[英]Unexpected stringstream behavior

考慮以下代碼:

#include <sstream>
#include <iostream>

using namespace std;

int main()
{
    stringstream ss;

    ss << string("12");
    int h;
    ss >> h;
    cout << h << endl;

    ss.str(string("")); // clear the content of ss

    ss << string("30");
    int m;
    ss >> m;
    cout << m << endl;

    return 0;
}

運行上面的代碼會產生一些隨機輸出:

12
0

在其他時間,觀察到以下輸出:

12
4

我希望輸出很簡單:

12 
30

為什么我得到了意外的結果?

另外,沒有必要的C ++ 11支持,將string s解析為int i的最佳方法應該是什么? 應該是int i = atoi(s.c_str())嗎?

當從流中提取12 ,到達其末尾,這使其處於錯誤狀態。 任何進一步的提取將失敗。 您需要在清除其內容時調用ss.clear()

如果您檢查了提取是否成功,則可以避免此問題。 我通常希望將任何從流中提取的內容視為某種情況。

是的,在C ++ 11之前,使用字符串流將字符串解析為整數是一種完全合理的方法。 我更喜歡使用atoi 對於任何想了解C ++ 11方式的人,請使用std :: stoi

對於那些與上面類似但又不完全相同的人,我發現當您在需要重用流的場景中(例如在while循環中)獲得流時,避免這種情況的最簡單方法是頭痛(除了ss.clear )是每次創建一個新的流。 例如:

int GetInteger(){
    cout << "Enter an int: " << endl;
    string userInput;
    while (true){
        stringstream ss;
        getline(cin,userInput);
        ss << userInput;
        //Making sure that an int was passed
        int result;
        if (ss >> result){
            //Making sure that there is no extra stuff after
            string extra;
            if (ss >> extra){
                cout << "Unexpected stuff at end of input: " << extra << endl;
            } else{
                return result;
            }
        } else {
            cout << "Number you entered is not an INT. Please enter an integer" << endl;
        }
        cout << "Retry: " << endl;
        // ss.clear();
    }
}

因此,每次用戶輸入無效的輸入時,在while循環的開始,我都會創建一個新的stringstream對象。 雖然研究我的函數的不確定行為,我發現這個問題,有一個類似的例子。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM