2014-06-17 3 views
2

Рассмотрим следующий код:Неожиданное поведение stringstream

#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 

Почему я получил неожиданные результаты?

Также, что должно быть лучшим способом разобрать string s до int i без необходимости поддержки C++ 11? Должно ли это быть int i = atoi(s.c_str())?

+0

_'Также, что должно быть лучшим способом для синтаксического анализа ...'_ Использовать 'std :: istringstream'. –

+0

Неправильно очистка потока, используйте 'ss.clear()' – yizzlez

ответ

6

Когда вы извлекаете из потока 12, вы достигаете его конца, что помещает его в плохое состояние. Дальнейшие экстракции не удастся. Вы должны позвонить ss.clear() примерно в то время, когда вы очистите его содержимое.

Если вы проверили успех своих выделений, вы бы избежали этой проблемы. Обычно я ожидаю увидеть любое извлечение из потока как своего рода условие.

И да, используя струнные потоки для синтаксического анализа строк как целых чисел, это вполне разумный способ сделать это pre-C++ 11. Я предпочел бы это, используя atoi. Для тех, кто хочет знать путь C++ 11, используйте std::stoi.

+0

Спасибо! Каким должен быть лучший способ разбора 'string s' на' int i'? Является ли 'stringstream' хорошей идеей? – lwxted

+0

@lwxted Да, я бы предпочел увидеть это над «atoi». –

+0

@lwxted Использование 'istringstream s (" 123 "); s >> value' или 'ostringstream s; s << значение; s.str() 'следует избегать проблемы в вопросе (избегайте stringstream). –

Смежные вопросы