Упражнение 5.14. Напишите программу для чтения строк со стандартного устройства ввода и поиска совпадающих слов. Программа должна находить во вводе места, где одно слово непосредственно сопровождается таким же. Отследите наибольшее количество повторений и повторяемое слово. Отобразите максимальное количество дубликатов или сообщение, что никаких повторений не было. Например, при вводе how now now now brown cow cow вывод должен указать, что слово now встретилось три раза.

<p><image l:href="#reader.png"/>5.4.2. Традиционный оператор <code>for</code></p>

Операторfor имеет следующий синтаксис:

for (инициализирующий-оператор условие; выражение)

 оператор

Слово for и часть в круглых скобках зачастую упоминают как заголовок for (for header).

Инициализирующий-оператор должен быть оператором объявления, выражением или пустым оператором. Каждый из этих операторов завершается точкой с запятой, поэтому данную синтаксическую форму можно рассматривать так:

for (инициализатор; условие; выражение)

 оператор

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

Поток выполнения в традиционном цикле for

Рассмотрим следующий цикл for из раздела 3.2.3:

// обрабатывать символы,

// пока они не исчерпаются или не встретится пробел

for (decltype(s.size()) index = 0;

     index != s.size () && !isspace(s[index]); ++index)

 s[index] = toupper(s[index]); // преобразовать в верхний регистр

Порядок его выполнения таков.

1. В начале цикла только однажды выполняется инициализирующий-оператор. В данном случае определяется переменная index и инициализируется нулем.

2. Затем обрабатывается условие. Если index не равен s.size() и символ в элементе s[index] не является пробелом, то выполняется тело цикла for. В противном случае цикл заканчивается. Если условие ложно уже на первой итерации, то тело цикла for не выполняется вообще.

3. Если условие истинно, то тело цикла for выполняется. В данном случае оно переводит символ в элементе s[index] в верхний регистр.

4. И наконец, обрабатывается выражение. В данном случае значение переменной index увеличивается 1.

Эти четыре этапа представляют первую итерацию цикла for. Этап 1 выполняется только однажды при входе в цикл. Этапы 2–4 повторяются, пока условие не станет ложно, т.е. пока не встретится символ пробела в элементе s или пока index не превысит s.size().

Не забывайте, что видимость любого объекта, определенного в пределах заголовка for, ограничивается телом цикла for. Таким образом, в данном примере переменная index недоступна после завершения цикла for.

Несколько определений в заголовке for

Подобно любому другому объявлению, инициализирующий-оператор способен определить несколько объектов. Однако только инициализирующий-оператор может быть оператором объявления. Поэтому у всех переменных должен быть тот же базовый тип (см. раздел 2.3). Для примера напишем цикл, дублирующий элементы вектора в конец следующим образом:

// запомнить размер v и остановиться,

// достигнув первоначально последнего элемента

for (decltype(v.size()) i = 0, sz = v.size(); i != sz; ++i)

 v.push_back(v[i]);

В этом цикле инициализирующий-оператор определяется индекс i и управляющая переменная цикла sz.

Пропуск частей заголовка for

В заголовке for может отсутствовать любой (или все) элемент: инициализирующий-оператор, условие или выражение.

Когда инициализация не нужна, вместо инициализирующего оператора можно использовать пустой оператор. Например, можно переписать цикл, который искал первое отрицательное число в векторе так, чтобы использовался цикл for:

auto beg = v.begin();

for ( /* ничего */; beg != v.end() && *beg >= 0; ++beg)

 ; // ничего не делать

Перейти на страницу:

Похожие книги