for(it = str.begin(); it != str.end() && isspace(*it); it++) ;
str.erase(str.begin(), it);
Что именно эта петля делает?Строковая функция для петель
for(it = str.begin(); it != str.end() && isspace(*it); it++) ;
str.erase(str.begin(), it);
Что именно эта петля делает?Строковая функция для петель
for(it = str.begin(); it != str.end() && isspace(*it); it++) ;
Эта линия позиционирует итератор на начало строки (str.begin()
). Условие it != str.end() && isspace(*it)
говорит простым языком «пока конец строки не достигнут И текущий символ - это пробел, увеличивайте итератор».
Следующая
str.erase(str.begin(), it);
Это стирает часть строки от ее начинают итератора. В ясных выражениях он обрезает любые пробелы в начале строки.
EDIT: Пожалуйста, прочитайте комментарий ниже, он добавит полезную информацию в ответ.
За исключением того, что 'isspace (* it)' является неопределенным поведением. («Правильный» способ пропускать ведущее белое пространство: 'it = std :: find_if (str.begin(), str.end(), [] (unsigned char ch) {! Isspace (ch);});' . (Я должен поблагодарить Альфа за трюк объявления лямбды взять «неподписанный символ» и, таким образом, избежать приведения, которое в противном случае было бы необходимо.) –
Этот код слишком умен для своего же блага - есть веские причины для того, чтобы не конденсировать код слишком сильно вертикально.
Loop-confusion является одним из них.
Перезапись немного
for(it = str.begin(); it != str.end() && isspace(*it); it++)
;
str.erase(str.begin(), it);
или, что эквивалентно
for(it = str.begin(); it != str.end() && isspace(*it); it++)
{
// Personally, I always put an "intentionally left empty" comment inside these.
}
str.erase(str.begin(), it);
становится ясно, что erase
находится за пределами петля.
Переписывая петлю с помощью while
it = str.begin();
while (it != str.end() && isspace(*it))
{
it++;
}
str.erase(str.begin(), it);
делает его более очевидным, что первый находит первый не пробел в строке, а затем стирает все до него, то есть урезает ведущие пробелы.
(я предпочитаю while
формировать себя.)
Мне особенно нравится, как вы заметили странность цикла, и предложили, как сделать это очень ясно *, внутри ничего не происходит. –
Этот код дез две вещи.
Первый находит первый символ в строке, которая не является белым пространством:
for(it = str.begin(); it != str.end() && isspace(*it); it++) ;
Второй удаляет все символы до этого символа:
str.erase(str.begin(), it);
Сочетание их: код удаляет символы пробела в начале строки :)
Строковая функция (sic) не является частью цикла. Вся работа выполняется в состоянии и приращения частей цикла. «Стирание» вызывается один раз после завершения цикла. – jrok
Учитывая 'begin()' и 'end()', это * not * C#, так почему он помечен как таковой? – crashmstr
Это * C++ *, а не * C# * –