Оператор цикла цикл с параметром на языке

Здравствуйте. Оператор цикла с параметром используется в тех случаях, когда некоторое однообразное действие надо повторить определенное количество раз. Особенно, если это количество достаточно велико. Бывают же такие задачи, когда необходимо, например, вычислить сумму каких-либо величин, каждая из которых вычисляется по формуле. Ведь если непосредственно вычислять сумму 1 + 2 + 3 + … + 1000, то программа разрастется до невообразимых масштабов.
Оператор цикла с параметром в народе ещё называют “оператор For”, и в Pascal он бывает двух типов (второй тип смотрите ниже). Первый записывается так:
for i := N1 to N2 do
<ОПЕРАТОР>
Всё, что находится между for и do, называется заголовком цикла, после do – телом цикла. Переменная i зазывается параметром цикла и имеет порядковый тип (целые числа, логический тип, символы, перечислимый и диапазонный тип). Слова for, to и do – это служебные слова Pascal, которые использовать в своих программах для обозначения переменных нельзя. Индекс i, которым обозначаются номера действий в операторе цикла, изменяется от меньшего N1 к большему N2 (N1 ≤ N2). Первый номер N1 по значению не должен превышать второй N2, иначе цикл не запустится и ОПЕРАТОР ни разу не выполнится.
Важно помнить: ИЗМЕНЯТЬ ПАРАМЕТР ЦИКЛА i В ТЕЛЕ ЦИКЛА НЕЛЬЗЯ! — это вызовет ошибку.
Оператор цикла этого типа действует как:
— сначала индекс i приравнивается N1 – минимальному возможному значению;
— потом проверяется, не превышает ли i второго номера N2 (i ≤ N2). Если это условие выполняется, то идем на следующий пункт, иначе (то есть при i > N1) – выходим из цикла;
— выполняется ОПЕРАТОР в теле цикла;
— далее увеличивается i на 1, и повторяем со второго пункта (т.е. проверяем истинность условия i ≤ N2, выполняем оператор, увеличиваем i на 1, и т.д).
В роли начального значения N1 наиболее часто используют 1 или 0 (это зависит от задачи).
Приведем пример с вычислением упомянутой ранее суммой 1 + 2 + 3 + … + 1000 первых 1000 натуральных чисел. Поскольку нужно сложить числа от 1 до 1000 включительно, то было бы естественно изменять индекс i от 1 до 1000. Тогда на каждой итерации цикла (при каждом выполнении) искомую сумму, которую мы обозначим sum, будем увеличивать на i. Вот, что у нас получится.
Посчитать сумму первых 1000 натуральных чисел
Код Pascal
1 2 3 4 5 6 7 8 9 10 | var i, sum: integer; begin |
После запуска программы вы должны увидеть результат: 500500. Что делает наша программа?
2 строка. Описываем переменные i (параметр цикла) и sum (конечная сумма) как целые;
5 строка. Начальному значению суммы sum присваиваем 0. Это называется инициализация начальной переменной;
6 строка. Числа будем складывать от 1 до 1000;
7 строка. На каждой последующей итерации цикла к сумме прибавляем i;
8 строка. После выхода из цикла (когда будет i = 1000) выводим конечный результат суммы.
Решим ещё одну простенькую задачку:
Напечатать ряд чисел 20 в виде: 20 20 20 20 20 20 20 20 20 20.
Код Pascal
1 2 3 4 5 6 7 | var i: byte; begin |
Мы видим, что количество выводимых чисел равно 10, поэтому запускаем цикл от 1 до 10, и выводим число 20 оператором вывода write(). Обратите внимание, что величина индекса изменяется лишь в пределах [1, 10], поэтому не имеет смысла использовать целый тип integer – достаточно обойтись типом byte (8 бит, или 1 байт). Особенность этого примера в том, что код программы не содержит переменной i в теле цикла (напоминаю, тело цикла – часть программы после do) – мы просто выводили несколько раз число 20. Бывает, когда параметр цикла используется в теле цикла, но во многих простеньких программах его использование лишнее.
А вот пример простой задачи, когда параметр цикла используется:
Напечатать “столбиком” все целые числа от 12 до 25.
Если промежуточное выводимое число обозначить n, то изменяя его с 12 по 25 включительно, выведем все числа. Только здесь нужно задействовать оператор вывода writeln – с переводом курсора на следующую строку.
Код Pascal
1 2 3 4 5 6 7 | var n: byte; begin |
И ещё один пример:
Напечатать таблицу умножения на 7.
Код Pascal
1 2 3 4 5 6 7 8 | var i: byte; begin |
Вместо “крестика” (знак умножения) можете использовать что-либо другое например, клавиатурные “звездочку” или букву “x”. После запуска программы у вас должно получится так:
7 × 1 = 7
7 × 2 = 14
7 × 3 = 21
7 × 4 = 28
7 × 5 = 35
7 × 6 = 42
7 × 7 = 49
7 × 8 = 56
7 × 9 = 63
7 × 10 = 70
Если вместо ОПЕРАТОРА в теле цикла необходимо выполнить несколько операторов, то их нужно заключить в операторные скобки BEGIN … END, и разделить между собой точкой с запятой (в конце последнего оператора, перед закрывающим end, точку с запятой ставить не обязательно). Образованая таким образом конструкция из нескольких операторов называется составным оператором:
for i := N1 to N2 do
begin
<ОПЕРАТОР 1>;
<ОПЕРАТОР 2>;
<ОПЕРАТОР 3>;
…………
<ОПЕРАТОР k>
end.
Операторы в составном операторе в цикла выполняются один за другим, после чего по возможности производится переход на следующую итерацию. Наведем примеры.
Рассчитать значения y для значений х, равных 4, 5, …, 28: y = 2t2 + 5.5t – 2, если t = x + 2.
Код Pascal
1 2 3 4 5 6 7 8 9 10 11 12 13 | var x, t: integer; y: real; begin |
2, 3 строки. Описываем x, t как целые, а y – вещественную;
6 строка. Изменяем x в указаных в условии пределах [4, 28];
8 строка. Предварительно вычисляем t, используя значение x;
9 строка. Вычисляем y, подставляя найденное ранее t;
10 строка. Выводим значения x и y.
Синтаксис другого типа оператора цикла с параметром задается следующим образом:
for i := N1 downto N2 do
<ОПЕРАТОР>
Отличие этого цикла от первого только в том, что значение индекса i не увеличивается, а уменьшается (на это указывает английское слово down, означающе “вниз”). Таким образом, начальное значение N1 параметра цикла i должно быть НЕ МЕНЬШЕ конечного N2 (N1 ≥ N2), ибо в противном случае цикл ни разу не выполнится.
Для примера решим такую задачу:
Вычислить сумму первых 1000000 членов гармонического ряда.
Гармоническим рядом в математике называют ряд, составленный из чисел, обратных к натуральным: 1 + 1/2 + 1/3 + … + 1/n + … . По условию нужно сложить первые 1000000 (один миллион) членов, только мы это сделаем в обратоном по отношению к указанному выше порядке: 1/1000000 + 1/999999 + … + 1/3 + 1/2 + 1.
Код Pascal
1 2 3 4 5 6 7 8 9 10 11 | var i: integer; sum: real; begin |
А вот как эта задача решается с циклом первого типа, посмотрите на странице for 10-14. Только нужно иметь ввиду, что, хотя гармонический ряд и является расходимым – его частичные суммы стремятся к бесконечности при неограниченном возрастании членов) – но растет гармонический ряд очень медленно.
Вообще, в каждом отдельном случае нужно решать, какой цикл с параметром использовать лучше – с возрастающим или убывающим параметром. В разделе Задачника в группе “for” есть много примеров на тему цикла с параметром, например, Функции с использованием факториала. А пока на этом все, если есть вопросы или пожелания, пишите в комментариях.
Источник
Рассмотрим третью алгоритмическую структуру — цикл.
Циклом называется блок кода, который для решения задачи требуется повторить несколько раз.
Каждый цикл состоит из
- блока проверки условия повторения цикла
- тела цикла
Цикл выполняется до тех пор, пока блок проверки условия возвращает истинное значение.
Тело цикла содержит последовательность операций, которая выполняется в случае истинного условия повторения цикла. После выполнения последней операции тела цикла снова выполняется операция проверки условия повторения цикла. Если это условие не выполняется, то будет выполнена операция, стоящая непосредственно после цикла в коде программы.
В языке Си следующие виды циклов:
- while — цикл с предусловием;
- do…while — цикл с постусловием;
- for — параметрический цикл (цикл с заданным числом повторений).
Цикл с предусловием while
Общая форма записи
while (Условие)
{
БлокОпераций;
}
Если Условие выполняется (выражение, проверяющее Условие, не равно нулю), то выполняется БлокОпераций, заключенный в фигурные скобки, затем Условие проверяется снова.
Последовательность действий, состоящая из проверки Условия и выполнения БлокаОпераций, повторяется до тех пор, пока выражение, проверяющее Условие, не станет ложным (равным нулю). При этом происходит выход из цикла, и производится выполнение операции, стоящей после оператора цикла.
Пример на Си: Посчитать сумму чисел от 1 до введенного k
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
#define _CRT_SECURE_NO_WARNINGS // для возможности использования scanf
#include <stdio.h>
int main() {
int k; // объявляем целую переменную key
int i = 1;
int sum = 0; // начальное значение суммы равно 0
printf(“k = “);
scanf(“%d”, &k); // вводим значение переменной k
while (i <= k) // пока i меньше или равно k
{
sum = sum + i; // добавляем значение i к сумме
i++; // увеличиваем i на 1
}
printf(“sum = %dn”, sum); // вывод значения суммы
getchar(); getchar();
return 0;
}
Результат выполнения
При построении цикла while, в него необходимо включить конструкции, изменяющие величину проверяемого выражения так, чтобы в конце концов оно стало ложным (равным нулю). Иначе выполнение цикла будет осуществляться бесконечно (бесконечный цикл).
Пример бесконечного цикла
1
2
3
4
while (1)
{
БлокОпераций;
}
while — цикл с предусловием, поэтому вполне возможно, что тело цикла не будет выполнено ни разу если в момент первой проверки проверяемое условие окажется ложным.
Например, если в приведенном выше коде программы ввести k=-1, то получим результат
Цикл с постусловием do…while
Общая форма записи
do {
БлокОпераций;
} while (Условие);
Цикл do…while — это цикл с постусловием, где истинность выражения, проверяющего Условие проверяется после выполнения Блока Операций, заключенного в фигурные скобки. Тело цикла выполняется до тех пор, пока выражение, проверяющее Условие, не станет ложным, то есть тело цикла с постусловием выполнится хотя бы один раз.
Использовать цикл do…while лучше в тех случаях, когда должна быть выполнена хотя бы одна итерация, либо когда инициализация объектов, участвующих в проверке условия, происходит внутри тела цикла.
Пример на Си. Проверка, что пользователь ввел число от 0 до 10
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
#define _CRT_SECURE_NO_WARNINGS // для возможности использования scanf
#include <stdio.h>
#include <stdlib.h> // для использования функции system()
int main() {
int num; // объявляем целую переменную для числа
system(“chcp 1251”); // переходим на русский язык в консоли
system(“cls”); // очищаем экран
do {
printf(“Введите число от 0 до 10: “); // приглашение пользователю
scanf(“%d”, &num); // ввод числа
} while ((num < 0) || (num > 10)); // повторяем цикл пока num<0 или num>10
printf(“Вы ввели число %d”, num); // выводим введенное значение num – от 0 до 10
getchar(); getchar();
return 0;
}
Результат выполнения:
Параметрический цикл for
Общая форма записи
for (Инициализация; Условие; Модификация)
{
БлокОпераций;
}
for — параметрический цикл (цикл с фиксированным числом повторений). Для организации такого цикла необходимо осуществить три операции:
- Инициализация – присваивание параметру цикла начального значения;
- Условие – проверка условия повторения цикла, чаще всего – сравнение величины параметра с некоторым граничным значением;
- Модификация – изменение значения параметра для следующего прохождения тела цикла.
Эти три операции записываются в скобках и разделяются точкой с запятой ;;. Как правило, параметром цикла является целочисленная переменная.
Инициализация параметра осуществляется только один раз — когда цикл for начинает выполняться.
Проверка Условия повторения цикла осуществляется перед каждым возможным выполнением тела цикла. Когда выражение, проверяющее Условие становится ложным (равным нулю), цикл завершается. Модификация параметра осуществляется в конце каждого выполнения тела цикла. Параметр может как увеличиваться, так и уменьшаться.
Пример на Си: Посчитать сумму чисел от 1 до введенного k
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
#define _CRT_SECURE_NO_WARNINGS // для возможности использования scanf
#include <stdio.h>
int main() {
int k; // объявляем целую переменную key
int sum = 0; // начальное значение суммы равно 0
printf(“k = “);
scanf(“%d”, &k); // вводим значение переменной k
for(int i=1; i<=k; i++) // цикл для переменной i от 1 до k с шагом 1
{
sum = sum + i; // добавляем значение i к сумме
}
printf(“sum = %dn”, sum); // вывод значения суммы
getchar(); getchar();
return 0;
}
Результат выполнения
В записи цикла for можно опустить одно или несколько выражений, но нельзя опускать точку с запятой, разделяющие три составляющие цикла.
Код предыдущего примера можно представить в виде
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
#define _CRT_SECURE_NO_WARNINGS // для возможности использования scanf
#include <stdio.h>
int main() {
int k; // объявляем целую переменную key
int sum = 0; // начальное значение суммы равно 0
printf(“k = “);
scanf(“%d”, &k); // вводим значение переменной k
int i=1;
for(; i<=k; i++) // цикл для переменной i от 1 до k с шагом 1
{
sum = sum + i; // добавляем значение i к сумме
}
printf(“sum = %dn”, sum); // вывод значения суммы
getchar(); getchar();
return 0;
}
Параметры, находящиеся в выражениях в заголовке цикла можно изменить при выполнении операции в теле цикла, например
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
#define _CRT_SECURE_NO_WARNINGS // для возможности использования scanf
#include <stdio.h>
int main() {
int k; // объявляем целую переменную key
int sum = 0; // начальное значение суммы равно 0
printf(“k = “);
scanf(“%d”, &k); // вводим значение переменной k
for(int i=1; i<=k; ) // цикл для переменной i от 1 до k с шагом 1
{
sum = sum + i; // добавляем значение i к сумме
i++; // добавляем 1 к значению i
}
printf(“sum = %dn”, sum); // вывод значения суммы
getchar(); getchar();
return 0;
}
В цикле for может использоваться операция запятая – , – для разделения нескольких выражений. Это позволяет включить в спецификацию цикла несколько инициализирующих или корректирующих выражений. Выражения, к которым применяется операция запятая, будут вычисляться слева направо.
Пример на Си:
1
2
3
4
5
6
7
8
9
10
11
12
13
#define _CRT_SECURE_NO_WARNINGS // для возможности использования scanf
#include <stdio.h>
int main() {
int k; // объявляем целую переменную key
printf(“k = “);
scanf(“%d”, &k); // вводим значение переменной k
for(int i=1, j=2; i<=k; i++, j+=2) // цикл для переменных
{ // (i от 1 до k с шагом 1) и (j от 2 с шагом 2)
printf(“i = %d j = %dn”, i, j); // выводим значения i и j
}
getchar(); getchar();
return 0;
}
Результат выполнения
Вложенные циклы
В Си допускаются вложенные циклы, то есть когда один цикл находится внутри другого:
for (i = 0; i<n; i++) // внешний цикл – Цикл1
{
for (j = 0; j<n; j++) // вложенный цикл – Цикл2
{
; // блок операций Цикла2
}
// блок операций Цикла1;
}
Пример: Вывести числа от 0 до 99, по 10 в каждой строке
1
2
3
4
5
6
7
8
9
10
11
12
13
14
#define _CRT_SECURE_NO_WARNINGS // для возможности использования scanf
#include <stdio.h>
int main() {
for(int i=0; i<10; i++) // цикл для десятков
{
for (int j = 0; j < 10; j++) // цикл для единиц
{
printf(“%2d “, i * 10 + j); // выводим вычисленное число (2 знакоместа) и пробел
}
printf(“n”); // во внешнем цикле переводим строку
}
getchar(); // scanf() не использовался,
return 0; // поэтому консоль можно удержать одним вызовом getchar()
}
Результат выполнения
Рекомендации по выбору цикла
При выборе цикла необходимо оценить необходимость проверки условия при входе в цикл или по завершении прохождения цикла.
Цикл с постусловием удобно применять в случаях, когда для проверки условия требуется вычислить значение выражения, которое затем будет размещено в теле цикла (см. выше пример ввода числа от 0 до 10).
Цикл c предусловием используется в случае если все переменные, участвующие в выражении, проверяющем условие, проинициализированы заранее, но точное число повторений цикла неизвестно или предполагается сложная модификация переменных, участвующих в формировании условия повторения цикла.
Если цикл ориентирован на работу с параметром, для которого заранее известно число повторений и шаг изменения, то более предпочтительным является параметрический цикл. Очень удобно использовать параметрический цикл при работе с массивами для перебора элементов.
Операторы прерывания и продолжения цикла break и continue
В теле любого цикла можно использовать операторы прерывания цикла – break и продолжения цикла – continue.
Оператор break позволяет выйти из цикла, не завершая его.
Оператор continue позволяет пропустить часть операторов тела цикла и начать новую итерацию.
Пример на Си: Вывести числа от 0 до 99 ниже главной диагонали
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
#define _CRT_SECURE_NO_WARNINGS // для возможности использования scanf
#include <stdio.h>
int main() {
for(int i=0; i<10; i++) // цикл для десятков
{
for (int j = 0; j < 10; j++) // цикл для единиц
{
if (j > i) // если число единиц больше числа десятков в числе
break; // выходим из вложенного цикла и переходим к новой строке
printf(“%2d “, i * 10 + j); // выводим вычисленное число (2 знакоместа) и пробел
}
printf(“n”); // во внешнем цикле переводим строку
}
getchar(); // scanf() не использовался,
return 0; // поэтому консоль можно удержать одним вызовом getchar()
}
Результат выполнения
Пример на Си: Вывести числа от 0 до 99 исключая числа, оканчивающиеся на 5 или 8
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
#define _CRT_SECURE_NO_WARNINGS // для возможности использования scanf
#include <stdio.h>
int main() {
for(int i=0; i<10; i++) // цикл для десятков
{
for (int j = 0; j < 10; j++) // цикл для единиц
{
if ((j == 5) || (j == 8)) // если число единиц в числе равно 5 или 8,
continue; // переходим к следующей итерации цикла
printf(“%2d “, i * 10 + j); // выводим вычисленное число (2 знакоместа) и пробел
}
printf(“n”); // во внешнем цикле переводим строку
}
getchar(); // scanf() не использовался,
return 0; // поэтому консоль можно удержать одним вызовом getchar()
}
Результат выполнения
При вложенных циклах действия операторов break и continue распространяется только на самую внутреннюю структуру, в которой они содержатся.
Оператор безусловного перехода goto
Общая форма записи
goto Метка;
. . .
Метка : Операция;
Выполнение оператора goto вызывает передачу управления в программе операции, помеченной Меткой. По сути Метка является идентификатором адреса операции, которой должно быть передано управление. Для отделения Метки от Операции используется двоеточие – :.
Метка может располагаться в программе как до оператора goto, так и после него. Имена Меток образуются по тем же правилам, что и имена переменных.
Пример на Си: Вывести все целые числа от 5 до 0.
1
2
3
4
5
6
7
8
9
10
11
12
#define _CRT_SECURE_NO_WARNINGS // для возможности использования scanf
#include <stdio.h>
int main() {
int k = 5;
M1: if (k < 0) // если k<0,
goto M2; // переходим на метку M2 (выходим из программы)
printf(“%d “, k); // выводим значение k
k–; // уменьшаем k на 1
goto M1; // переходим на метку M1 (повторяем операции выше)
M2: getchar();
return 0;
}
Результат выполнения
Использование оператора goto в программах на Си без крайней необходимости не рекомендуется, поскольку это может повлечь за собой ряд ошибок, связанных с плохой читаемостью кода программы. Использование операторов цикла позволяет практически полностью исключить необходимость использования оператора goto.
Назад: Язык Си
Источник