Основные этапы проектирования программ Проектирование и последующая поддержка программного обеспечения включает несколько этапов: 1) разработка спецификации (specification); 2) проектирование или конструирование программы (design); 3) доказательство правильности проекта (verification); 4) кодирование, т. е. описание программ на языке программирования (coding); 5) отладка и проверка правильности программ (debugging and testing); 6) доработка и улучшение программ (refining); 7) производство окончательного программного продукта (production); 8) поддержка программного продукта в процессе его использования (maintenance). Рассмотрим перечисленные этапы более подробно. На первом этапе детально анализируется основная цель разработки программы и составляется подробное описание всех действий, которые она должна выполнять. Такое содержательное описание называется спецификацией. При разработке спецификации необходимо дать ответы на следующие вопросы: какими должны быть входные данные; какие данные являются корректными и какие ошибочными; кто будет использовать разработанное программное обеспечение и каким должен быть интерфейс (средство общения с пользователем); какие ошибки необходимо выявлять и какие сообщения желательно выдавать пользователю при наличии ошибок; какие упрощения, предположения и допущения можно сделать по отношению к программам; перечислить все особые ситуации, которые требуют дополнительного учета и специального рассмотрения; какими должны быть выходные данные; какая документация по программам должна быть подготовлена; как развивать и улучшать программы в будущем. На этапе проектирования необходимо построить структуру программы, выбрать или разработать все алгоритмы, которые она будет реализовывать, решить все вопросы по организации данных. Здесь эффективным подходом является разделение сложной исходной задачи на некоторые подзадачи. В частности, общую схему любой программы можно (и даже полезно) представить в виде трех последовательных блоков, причем правильность этой схемы сомнений не вызывает: Блок 1. Задание исходных данных. Блок 2. Решение поставленной задачи. Блок 3. Вывод полученных результатов. Выделение первого блока полезно для того, чтобы в самом начале проектирования программы подумать о том, что представляют собой ее исходные данные, в каком виде они должны быть представлены во внешней среде и в программе. Если исходные данные при каждом запуске программы должны задаваться человеком, то следует позаботиться об удобстве пользователя. При вводе исходных данных нетрудно допустить ошибку, поэтому при проектировании программы следует продумать, как должна вести себя программа при вводе ошибочных данных, предусмотреть реакцию программы на ошибку. Многое из того, что говорилось об исходных данных, относится и к окончательным результатам. После разработки общей структуры программы необходимо выполнить следующие этапы: 1) установить, какие библиотечные (ранее разработанные) средства можно использовать и какие новые процедуры необходимо разработать; 2) разработать новые структуры данных и алгоритмы выполнения новых процедур; 3) обосновать (доказать) правильность проекта. При доказательстве правильности проекта в первую очередь необходимо проверить критические части алгоритмов, какими являются циклы и условные переходы. Выявление ошибок на этом этапе позволяет существенно упростить последующие этапы кодирования и отладки программ; 4) произвести кодирование, т. е. описание алгоритмов и данных с помощью инструкций выбранного языка программирования. Многие рассматривают этот этап как главный в программировании, хотя в действительности он является относительно второстепенным; 5) произвести отладку и проверку (тестирование) программы, цель которых — устранение логических ошибок. Основным инструментом здесь являются отладчики, которые позволяют проверить программу в некоторых специальных режимах ее выполнения (пошаговый режим). В процессе выполнения этапов 1—5 накапливается определенный опыт, который дает основание для усовершенствования программы (этап 6). В этом случае дорабатываются или изменяются некоторые алгоритмы и модули. Усовершенствование не должно приводить к повторению цикла разработки с самого начала. После завершения программного продукта он передается пользователям (этап 7). Последующая поддержка программного обеспечения (этап 8) сводится к устранению возможных ошибок, выявленных пользователями на этапе эксплуатации. Другая цель поддержки — постепенное улучшение (развитие и модификация) программного продукта. 2 Итак, подведем итог и сформулируем требования к выполнению лабораторных работ, обязательные для каждого, кто начинает программировать. Для выполнения лабораторной работы необходимо проделать следующие этапы: 1. Внимательно прочитать теоретический материал, приведенный перед лабораторной работой, текст лекций по данной теме, соответствующую главу учебника. 2. Определить количество необходимых переменных для решения задачи, их имена и тип. 3. Определить входные данные, область допустимых значений и способ их задания. 4. Определить выходные данные, формат вывода, способ вывода на экран. 5. Записать словесно по шагам ход решения задачи. Начать следует с разбиения задачи на блоки ввода данных, собственно решения задачи и вывода данных. Каждый блок затем конкретизируется путем разбиения на подзадачи до тех пор, пока решение задачи не будет продумано и записано в мельчайших деталях. 6. Написать текст программы решения задачи. 7. Определить заранее значение выходных данных при тестовых значениях входных данных. 8. Откомпилировать и запустить программу на выполнение. 9. Провести тестовый прогон программы, сравнить полученные результаты с ожидаемыми. 10.Проверить работу программы для «пограничных» значений данных, особое внимание уделить конечным значениям параметров циклов. 11.При необходимости воспользоваться трассировкой программы, проверить правильность работы при пошаговом выполнении. Тема: Числовые типы данных. Выражения. Стандартные функции. Решение задач линейной структуры Числовые типы Наиболее распространенные в математике типы чисел – это целые числа, которые представляют бесконечное множество дискретных значений, и действительные числа, которые представляют неограниченный континуум значений. Описание целых типов В пределах одного языка могут быть реализованы различные подмножества множества целых чисел. Диапазон возможных значений целых типов зависит от их внутреннего представления, которое может 3 занимать один, два или четыре байта. Так, в Турбо Паскале 7.0 используются следующие целые типы: ЦЕЛЫЕ ТИПЫ Название Длина, байт Диапазон значений Byte 1 0 . . 255 ShortInt 1 -128 . . +127 Word 2 0 . . 65535 Integer 2 -32768 . . +32767 LongInt 4 -2 147 483 648 . . +2 147 483 647 С целыми числами можно выполнять следующие операции: Арифметические: сложение (+); возведение в степень; вычитание (-); унарный плюс (+); умножение (*); унарный минус (-). остаток от деления (mod); Операции отношения: отношение равенства (=); отношение больше (>); отношение неравенства (<>); отношение не меньше (>=); отношение меньше (<); отношение не больше (<=). При действиях с целыми числами тип результата будет соответствовать типу операндов, а если операнды относятся к различным целым типам, - типу того операнда, который имеет максимальную мощность (максимальный диапазон значений). Возможное переполнение результата никак не контролируется (это важно!), что может привести к ошибкам. Особое внимание следует уделить операции деления целых чисел. В Турбо Паскале допускается две операции деления, которые соответственно обозначаются ‘/’ и div. Нужно знать, что результатом деления ‘/’ является не целое, а вещественное число (это справедливо, даже если вы делите 8 на 2, т.е. 8/2=4.0). Деление div – это целочисленное деление, т.е. тип результата целый. Описание действительных типов К вещественному типу относится подмножество вещественных чисел, которые могут быть представлены в так называемом формате с плавающей запятой и фиксированным числом цифр. С плавающей точкой каждое число представляется в виде двух групп цифр. Первая группа цифр называется мантиссой, вторая – порядком. В общем виде число в форме с плавающей точкой может быть представлено так: X= {+|-}MP{+ | -} r , где M – мантисса числа; r – порядок числа (r – целое число); P – основание системы счисления. Например, для десятичного основания представление 2Е-1 (здесь Е – основание десятичной системы счисления) будет иметь вид: 2*10 1 =0.2, а представление 1.234Е5 будет соответствовать: 1.234*105=123400.0. 4 В Турбо Паскале используются следующие типы вещественных чисел, которые определяют произвольное число лишь с некоторой конечной точностью, зависящей от внутреннего формата вещественного числа: Длина, Название Количество Диапазон десятичного байт значащих цифр порядка 4 Single 7..8 -45..+38 6 Real 11 .. 12 -39 . . +38 8 Double 15 . .16 -324 . . +308 10 Extended 19 . .20 -4951 . . +4932 8 Comp 19 . . 20 -2*1063 +1..+2*1063 -1 При описании вещественной переменной типа real в памяти компьютера будет создана переменная размерностью 4 байта. При этом 3 байта будут отданы под мантиссу, а один – под порядок. Над действительными числами можно выполнять следующие операции: Арифметические: сложение (+); возведение в степень; вычитание (-); унарный плюс (+); умножение (*); унарный минус (-). деление (/); Операции отношения: отношение равенства (=); отношение неравенства (<>); отношение меньше (<); отношение больше (>); отношение не меньше (>=); отношение не больше (<=). Как видим, Турбо Паскаль характеризуется богатой гаммой вещественных типов, однако доступ к типам single, double и extended возможен только при особых режимах компиляции. Эти типы рассчитаны на аппаратную поддержку арифметики с плавающей точкой и для их эффективного использования в состав ПК должен входить математический сопроцессор. Особое положение в Турбо Паскале занимает тип comp, который трактуется как вещественное число без экспоненциальной и дробной частей. Фактически, comp – это «большое» целое число со знаком, сохраняющее 19..20 значащих десятичных цифр. В то же время тип comp в выражениях полностью совместим с другими вещественными типами: над ним определены все вещественные операции, он может использоваться как аргумент математических функций и т.д. О преобразовании числовых типов В Паскале почти невозможны неявные (автоматические) преобразования типов. Исключение сделано только для типа integer, который разрешается использовать в выражениях типа real. Например, если переменные описаны следующим образом: Var X : integer; Y: real; 5 то оператор Y := X+2; будет синтаксически правильным, хотя справа от знака присваивания стоит целочисленное выражение, а слева – вещественная переменная, компилятор сделает преобразование типов автоматически. Обратное же преобразование автоматически типа real в тип integer в Турбо Паскале невозможно. Вспомним, какое количество байт выделяется под переменные типа integer и real: под целочисленный тип integer выделяется 2 байта памяти, а под real – 6 байта. Для преобразования real в integer имеются две встроенные функции: round (x) округляет вещественное x до ближайшего целого, trunc (x) усекает вещественное число путем отбрасывания дробной части. Выражения и операторы действия Простейшие средства описания действий, которые вычисляют единственное значение – выражения. Они образуются из констант, переменных и других объектов данных, а также знаков операций и скобок. Операнды выражений должны быть того типа, который требуется в данном контексте. Для арифметических выражений используются арифметические операции и математические функции: Арифметические операции бывают унарными и бинарными. Выражение -А Типы операндов R, I Тип результата R, I +А R, I R, I A+B I, I R, R; R, I; I, R I, I R, R; R, I; I, R I, I R, R; R, I; I, R R, R; R, I; I, R; I, I I, I I R I R I R R I A-B A*B Операция Унарный минус (изменение знака числа) Унарный плюс (изменение знака числа) Сложение Вычитание Умножение Деление Целочисленное деление A mod B I, I I Остаток от целочисленного деления А и В обозначают операнды, для типов величин используются обозначения: I – любой целый или натуральный, R – любой вещественный. A/B A div B 6 Стандартные математические функции Турбо Паскаля Обращение Тип Тип Примечание аргумента результата Abs(x) Real, integer Тип Модуль аргумента аргумента ArcTan(x) Real, integer Real Арктангенс (значение в радианах) Cos(x) Real, integer Real Косинус, угол в радианах Exp(x) Real, integer Real Экспонента Frac(x) Real Real Дробная часть числа Int(x) Real, integer Real Целая часть числа Ln(x) Real, integer Real Логарифм натуральный Pi Нет Real 3,141592653… Sin(x) Real, integer Real Синус, угол в радианах Sqr(x) Real, integer Тип Квадрат аргумента аргумента Sqrt(x) Real, integer Real Корень квадратный random Нет Real Псевдослучайное число в интервале [0, 1] Random(I) Integer Integer Псевдослучайное число в интервале [0, I] Round(x) Real Integer Округление до ближайшего целого Trunc(x) Real Integer Отбрасывание дробной части числа Порядок вычислений в выражениях следующий: 1) вычисляются подвыражения, заключенные в скобки; 2) затем выполняются операции с наибольшим приоритетом; обычно используются следующие уровни приоритетов (в порядке убывания): - возведение в степень; - мультипликативные операции: * , / , div , mod; - унарные операции: + , - , abs , not; - аддитивные операции: +, -; - операции отношения: = , <> , < , > , <= , >= ; - логические операции: and, or, not; 3) операции с одинаковым приоритетом выполняются слева направо. Хотя нет ограничений на сложность выражений, однако выражения, содержащие более 7 операндов, трудны для чтения и понимания и поэтому такие выражения не рекомендуется использовать. 7 Замечание (это важно!) 1) в Паскале нет операции или функции возведения в степень, поэтому используется следующее математическое тождество: xy= ey lnx 2) в Паскале существует только функция вычисления натурального логарифма, поэтому используется следующее математическое тождество: loga b= ln b/ln a Пример: Математическое выражение x3/2 – 7x + tg (x+2) Выражение на Паскале exp(3*ln(x)/2)-7*x+sin(x+2)/cos(x+2) Операторы действия – это средства языка, позволяющие изменять в процессе выполнения программы состояние вычислений. Самый простой оператор действия – оператор присваивания. <имя_переменной>:= <выражение> Оператор присваивания, несмотря на кажущуюся простоту, имеет очень важное алгоритмическое значение. Удобно считать, что выполнение присваивания переменной некоторого значения означает помещение этого значения в выделенный для переменной ящик. При этом каждый запоминающий ящик обладает следующими свойствами. 1. В каждый момент времени в ящике может храниться не более одного значения. 2. Каждый ящик способен хранить только значения одного и того же типа. Попытка поместить в ящик значение любого другого типа приводит к тому, что ящик отказывается принимать на хранение передаваемое ему значение – это расценивается как ошибка в программе. 3. Значение, помещенное в ящик, будет храниться в нем до тех пор, пока в этот ящик не будет помещено новое значение (в момент присваивания соответствующей переменной этого нового значения) – при этом предыдущее содержимое ящика безвозвратно теряется (уничтожается). 4. Находящееся в ящике значение считается текущим значением соответствующей переменной. Это текущее значение может быть выдано из ящика для использования сколько угодно раз, но при этом содержимое ящика не меняется: из него каждый раз выдается копия хранящегося значения с сохранением оригинала в ящике без какого-либо изменения. 5. К началу выполнения программы содержимое всех запоминающих ящиков считается неопределенным; в частности, их нельзя считать и пустыми, поскольку эти ящики могли использоваться при выполнении предыдущих программ, после чего в ящиках могло что-то остаться. Еще один оператор действия, хотя его можно лишь условно назвать таковым: он не выполняет никакого действия, это – пустой оператор (в 8 Паскале он обознается знаком «;»). В Паскале оператором действия является также оператор процедуры. Последний из простейших операторов действия – оператор останова, который прерывает работу программы (в Паскале это оператор halt). Ввод и вывод данных Ввод данных с клавиатуры производится с помощью стандартной процедуры read(<список ввода>) или ее разновидности readln(<список ввода>). Элементы списка ввода – идентификаторы (имена) переменных, перечисляемые через запятую. При выполнении этого оператора пользователь набирает на клавиатуре соответствующую последовательность значений, разделяя их пробелами (это важно!). Вывод данных на экран производится с помощью стандартной процедуры write(<список вывода>) или ее разновидности writeln(<список вывода>). Список вывода может содержать константы, переменные, выражения, формат вывода. Выражения в списке вывода разделяются запятыми. Окончание ln в имени процедуры означает, что курсор автоматически будет переведен в начало следующей строки экрана. 1. Определить количество необходимых переменных, их имена и тип. 2. Определить входные данные, область допустимых значений и способ их задания. 3. Записать на Паскале заданное выражение. 4. Определить выходные данные, формат вывода, способ вывода на экран. 5. Определить заранее значение выражения при тестовых значениях входных данных. Образец выполнения задания b b2 4ac Задание: вычислить значение выражения a3c 2a 1. 2. 3. Для вычисления данного выражения мне потребуются переменные a,b и с, которые могут принимать любые вещественные значения, кроме a=0, тип переменных real. Для хранения результата вычислений мне потребуется переменная y, которая также будет вещественного типа, так как операндами выражения являются вещественные переменные, над которыми выполняются операции вещественного типа. Входными данными являются переменные a,b и c. Их значения должны быть заданы до начала вычисления выражения. Задавать значения переменных буду с клавиатуры с помощью процедуры readln(). Искомое выражение на Паскале будет иметь вид: (b+sqrt(sqr(b)+4*a*c))/(2*a)-sqr(a)*a*c 9 4. 5. Выходными данными является переменная y. Вывод на экран осуществляется с помощью процедуры writeln(). Для наглядности и удобства восприятия результата задам формат вывода переменной: общая длина числа – 8, количество знаков после запятой – 4. Если задать значения переменных a=1, b=0, c=1, то значение выражения должно быть равно 0.0 Текст программы: Program zadacha1 _2; Var A,b,c,y: real; {описываем переменные, используемые в программе} Begin {начало основной программы} Writeln(‘введите значение переменной a, не равное 0’); Readln (a); {ввод с клавиатуры переменной а} Writeln (‘введите значения переменных b и c через пробел’); Readln (b,c); {ввод с клавиатуры переменных b,c} Y:= (b+sqrt(sqr(b)+4*a*c))/(2*a)-sqr(a)*a*c; {вычисление значения выражения} Writeln(‘значение искомого выражения равно’, y:8:4); {вывод результата на экран} End. Дальнейшие действия: Откомпилировать программу (клавиша <F9>), исправить ошибки, допущенные при наборе. Запустить программу на исполнение (сочетание клавиш <Ctrl>+<F9>). Задать тестовые значения переменных. Посмотреть результат выполнения программы, нажав сочетание клавиш <Alt>+<F5>, оценить полученн Задание: составить программу решения задачи. Указания к решению: перед составлением программы необходимо выполнить следующие этапы: 1. Определить количество необходимых переменных, их имена и тип. 2. Определить входные данные, область допустимых значений и способ их задания. 3. Определить выходные данные, формат вывода, способ вывода на экран. 4. Записать словесно по шагам ход решения задачи. 10 5. Определить заранее значение выходных данных при тестовых значениях входных данных. Образец выполнения задания Задача: Найти сумму цифр трехзначного натурального числа. 1. Для хранения самого числа мне потребуется переменная N, которая может принимать значения от 100 до 999, поэтому ее тип можно определить как диапазон 100..999 или как word. Для хранения значений трех цифр в записи числа N мне потребуются три переменные ed (единицы), des (десятки) и sot (сотни). Каждая из этих переменных может принимать значения от 0 до 9, поэтому их тип можно определить как диапазон 0..9 или как byte. Для хранения значения суммы цифр мне потребуется переменная S, которая может принимать значения от 1 до 27, поэтому ее тип можно определить как byte. 2. Входными данными в этой задаче является число N. Его значение должно быть задано до начала вычислений. Ввод числа буду осуществлять с клавиатуры с помощью процедуры readln(). 3. Выходными данными в задаче является значение суммы цифр, т.е. переменная S. Вывод переменной буду осуществлять с помощью процедуры writeln(). Т.к. переменная S натуральное число, то формат вывода можно не задавать. 4. Ход решения задачи: - ввод числа N; - задам начальное значение переменной S=0; - найду число единиц в данном числе, как остаток от деления на десять: ed= N mod 10; - найду число десятков в данном числе. Для этого отброшу единицы N div 10, а от оставшегося результата найду остаток от деления на 10: des=(N div 10) mod 10 - найду число сотен в данном числе как целую часть от деления на 100: sot= N div 100; - найду сумму цифр данного числа: S= ed+des+sot; - выведу на экран значение переменной S. 5. Тестовая проверка: пусть число N=735. Проверим вычисления. ed=N mod 10=735 mod 10=5; des= (N div 10) mod 10 = (735 div 10) mod 10 = 73 mod 10=3; sot= N div 100= 735 div 100=7; S=ed+des+sot=5+3+7=15. Текст пррограммы: Program zadacha1_3; Var N: word; 11 ed, des, sot: 0..9; s: byte; begin {начало программы} writeln(‘введите трехзначное число’); readln(N); s:=0; ed:=N mod 10; des:= (N div 10) mod 10; sot:= N div 100; s:= ed+des+sot; writeln(‘сумма цифр числа ‘, N, ‘ равна ‘, s); end. Дальнейшие действия: Откомпилировать программу (клавиша <F9>), исправить ошибки, допущенные при наборе. Запустить программу на исполнение (сочетание клавиш <Ctrl>+<F9>). Задать тестовые значения переменных. Посмотреть результат выполнения программы, нажав сочетание клавиш <Alt>+<F5>, оценить полученный результат. Запустить программу повторно, задать произвольные значения переменных, записать полученные результаты. Вариант 1 Объем первого файла составляет m1 Кбайт, n1 байт. Объем второго файла – m2 Кбайт, n2 байт. Определить объем файла, полученного слиянием данных двух. Вариант 2 Объем файла составляет m Кбайт, n байт. Архивация уменьшает его объем на 20%. Определить объем файла после архивации. Вариант 3 Текущее показание электронных часов: m часов (0 m23), n минут (0 n 59), k секунд (0 k 59). Какое время будут показывать часы через p часов, q минут, r секунд? Вариант 4 Дана величина A, выражающая объем информации в байтах. Определить сколько полных Мбайт, Кбайт и байт содержит величина A? 12 Вариант 5 Дано трехзначное натуральное число. Найти разность между заданным числом и суммой его цифр. Вариант 6 Дано положительное вещественное число, имеющее целую и дробную части. Поменять местами цифры из целой и дробной части, стоящие справа и слева от дробной точки. Вариант 7 Выяснить, на какой угол повернется часовая стрелка от положения 0 часов, 00 минут до того момента, когда пройдет h часов (h<12), m минут (m<60). Вариант 8 Дано трехзначное натуральное число. Получить другое натуральное число, в котором порядок цифр изменен на противоположный. Вариант 9 Дано вещественное число с двумя цифрами в целой части и двумя цифрами в дробной части. Найти сумму цифр этого числа. Вариант 10 Выяснить сколько полных часов и полных минут прошло от начала суток до того момента, когда часовая стрелка повернулась на f градусов (f<360). Вариант 11 Дано вещественное число с двумя цифрами в целой части и одной цифрой в дробной части. Получить вещественное число, запись которого являлась бы зеркальным отображением исходного числа (например, 36.2 и 2.63). Вариант 12 Идет k-я секунда суток. Определить, сколько полных часов и полных минут прошло от начала суток. Вариант 13 Присвоить переменной d третью от конца цифру в записи положительного целого числа. Вариант 14 Определить сколько часов, минут и секунд прошло между двумя данными моментами времени: h1 часов, m1 минут, s1 секунд и h2 часов, m2 минут, s2 секунд. 13 Вариант 15 Исходный объем информации составлял m Кбайт, n байт, k бит. Часть информации была утеряна, после чего объем составил m1 Кбайт, n1 байт, k1 бит. Определить объем утерянной информации. Тема: Логические выражения. Логический тип. Условный оператор. Оператор выбора. Программирование разветвляющихся алгоритмов Логические выражения Логические выражения (условия) – это выражения, которые могут принимать лишь одно из двух значений: true (истина) или false (ложь). Для построения логических выражений используются операции отношения, которые обозначаются знаками: = (отношение на равенство), <> (отношение на неравенство), < (отношение меньше), > (отношение больше), <= (отношение меньше или равно), >= (отношение больше или равно). Сложные условия составляются из простых с помощью логических операций: and (логическое «И»), or (логическое «ИЛИ») и not (логическое «НЕ»). При составлении сложных условий операнды логического выражения берутся в скобки (это важно!). Примеры логических выражений: 5>3; 2<=6; (x<2) and (x>=0); 2*x+5<>0 и т.п. При вычислении логических выражений операции выполняются в следующем порядке: not, and, or, операции отношения, арифметические операции. Если порядок выполнения операций нужно изменить, то применяют скобки. Логический тип В Турбо Паскале логический тип носит название BOOLEAN. Значением логического типа может быть одна из двух констант FALSE (ложь) или TRUE (истина). Для них справедливы правила: Ord(false)=0 Succ(false)=true Ord(true)=1 False<true Pred(true)=false Все реализации языка Pascal, в том числе и Turbo Pascal, вплоть до версии 6.0 содержали только один булевский тип Boolean, элементы которого могут принимать лишь два логических значения: True (истина) и False (ложь). В Turbo Pascal версии 7.0 добавлены еще три булевских типа ByteBool, WordBool и LongBool. Название Значению False Значению True 14 Размер памяти соответствует соответствует Boolean Число 0 1 1 байт ByteBool Число 0 Любое число, 1 байт отличное от 0 WordBool Число 0 в обоих 2 байта байтах LongBool Число 0 во всех 4 байта байтах Отметим, что новые булевские типы были введены для обеспечения совместимости разрабатываемых программ с Windows, в которой значению False соответствует 0, а значению True – любое, отличное от 0, число. Логические переменные должны быть описаны предложением: Var <имя_переменной>: boolean; Величины логического типа можно присваивать, выводить, но нельзя вводить процедурой read. Например: X:= true; y:=5>3 и т.п. Условный оператор Условные операторы позволяют выбирать для выполнения те или иные части программы в зависимости от некоторых условий. Если, например, в программе используются вещественные переменные x, y и z, и на каком-то этапе решения задачи требуется вычислить z= max(x, y), то желаемый результат получается в результате выполнения либо оператора присваивания z:= x, либо оператора присваивания z:= y. Поскольку значения переменных x и y заранее неизвестны, а определяются в процессе вычислений, то в программе необходимо предусмотреть оба эти оператора присваивания. Однако на самом деле должен выполниться один из них. Поэтому в программе должно содержаться указание о том, в каком случае надо выбирать для исполнения тот или иной оператор присваивания. Это указание естественно сформулировать с использованием отношения x>y. Если это отношение при текущих значениях x и y справедливо (принимает значение true), то для исполнения должен выбираться оператор z:= x; в противном случае для исполнения должен выбираться оператор z:= y (при x=y безразлично, какой оператор выполнять, так что выполнение оператора z:= y в этом случае даст правильный результат). Для задания подобного рода разветвляющихся вычислительных процессов в языках программирования существуют условные операторы. Рассмотрим полный условный оператор: if B then S1 else S2 Здесь if (если), then (то) и else (иначе) являются служебными словами, В – логическое выражение, а S1 и S2 – операторы. Выполнение такого условного оператора сводится к выполнению одного из входящих в него операторов S1 или S2: если заданное в операторе условие выполняется (логическое выражение В принимает значение true), то выполняется оператор S1, в противном случае выполняется оператор S2. 15 Алгоритм решения упомянутой выше задачи вычисления z= max(x, y) можно задать в виде условного оператора if x>y then z:= x else z:= y При формулировании алгоритмов весьма типичной является такая ситуация, когда на определенном этапе вычислительного процесса какиелибо действия надо выполнить только при выполнении некоторого условия, а если это условие не выполняется, то на данном этапе вообще не нужно выполнять никаких действий. Простейшим примером такой ситуации является замена текущего значения переменной х на абсолютную величину этого значения: если x<0, то необходимо выполнить оператор присваивания x:= -x; если же x>=0, то текущее значение х должно остаться без изменений, т.е. на данном этапе вообще не надо выполнять каких-либо действий. В подобных ситуациях удобна сокращенная форма записи условного оператора: if B then S Правило выполнения сокращенного условного оператора достаточно очевидно: если значение логического выражения В есть true, то выполняется оператор S; в противном случае никаких иных действий не производится. В языке программирования Паскаль в условном операторе между then и else, а также после else по синтаксису может стоять только один оператор. Если же при выполнении (или невыполнении) заданного условия надо выполнить некоторую последовательность действий, то их надо объединить в единый, составной оператор, т.е. заключить эту последовательность действий в операторные скобки begin...end (это важно!). Если, например, при x<y надо поменять местами значения этих переменных, то условный оператор будет записан следующим образом: if x<y then begin r:=x; x:=y; y:=r end Наличие сокращенной формы условного оператора требует большой осторожности при использовании. Например, условный оператор вида if B1 then if B2 then S1 else S2 допускает, вообще говоря, две разные трактовки: - - как полный условный оператор вида if B1 then begin if B2 then S1 end else S2 как сокращенный условный оператор вида if B1 then begin if B2 then S1 else S2 end По правилам Паскаля имеет место вторая трактовка, т.е. считается, что каждое слово else соответствует первому предшествующему ему слову then. Для избежания возможных ошибок и недоразумений можно 16 порекомендовать во всех подобных случаях четко выделять желаемую форму условного оператора путем взятия в операторные скобки. Оператор выбора Оператор выбора позволяет выбрать одно из нескольких возможных продолжений программы. Параметром, по которому осуществляется выбор, служит ключ выбора – выражение любого порядкового типа. Структура оператора выбора в Паскале такова: Case <ключ_выбора> of <список_выбора> [else <оператор_иначе>] end Здесь case, of, else, end – зарезервированные слова (случай, из, иначе, конец); <ключ_выбора> - выражение порядкового типа; <список_выбора> - одна или более конструкций вида: <константа_выбора>: <оператор>; <константа_выбора> - константа того же типа, что и выражение <ключ_выбора>; <операторы> - произвольные операторы Паскаля. Оператор выбора работает следующим образом. Вначале вычисляется значение выражения <ключ_выбора>, а затем в последовательности <список_выбора> отыскивается константа, равная вычисленному значению. Выполняется оператор, который следует за найденной константой, после чего оператор выбора завершает работу. Если в списке выбора не будет найдена константа, соответствующая вычисленному значению ключа выбора, управление передается операторам, стоящим за словом else. Часть else <оператор_иначе> можно опустить, тогда при отсутствии в списке выбора нужной константы не будет выполнено никаких действий, и оператор выбора просто завершит свою работу. Например, составим программу, которая по номеру дня недели выводит на экран его название: Program dni_nedeli; Var n: byte; Begin Readln(n); Case n of 1: writeln(‘понедельник’); 2: writeln(‘вторник’); 3: writeln(‘среда’); 4: writeln(‘четверг’); 5: writeln(‘пятница’); 6: writeln(‘суббота’); 7: writeln(‘воскресенье’); else writeln(‘дня недели с номером’,n,’нет’); end; 17 end. Следует помнить, что все константы из списка выбора должны быть различны. Любому из операторов списка выбора может предшествовать не одна, а несколько констант выбора, разделенных запятыми. Например, следующая программа при вводе одного из символов ‘y’ или ‘Y’ выведет на экран «Да», а при вводе ‘n’ или ‘N’ – слово «Нет». Var ch: char; Begin Readln(ch); Case ch of N, n: writeln(‘Да’); Y, y: writeln(‘Нет’); End; End. Очевидно, что рассмотренные выше программы можно записать с помощью вложенных или последовательно расположенных условных операторов, но в подобных задачах использование оператора выбора является более простым. Основное отличие условного оператора от оператора выбора состоит в том, что в условном операторе условия проверяются одно за другим, а в операторе выбора значение ключа выбора непосредственно определяет одну из возможностей. Лабораторная работа №2 Тема: Логические выражения. Логический тип. Условный оператор. Оператор выбора. Программирование разветвляющихся алгоритмов Задание 1 Указание к выполнению: задание 1 выполняется в тетради по вариантам. Вариант 1 1. Вычислить значение выражения при a= true и b= false: a or b and not a 2. Записать на Паскале отношение, истинное при выполнении указанного условия и ложное в противном случае: точка (x,y) лежит вне круга радиуса r с центром в точке (1,0) 18 Вариант 2 1. Вычислить значение выражения при a= true и b=false: (a or b) and not a 2. Записать на Паскале отношение, истинное при выполнении указанного условия и ложное в противном случае: уравнение ax2+bx+c=0 (a0) не имеет вещественных корней. Вариант 3 1. Вычислить значение выражения при a= true и b=false: not a and b 2. Записать на Паскале отношение, истинное при выполнении указанного условия и ложное в противном случае: x принадлежит отрезку [2,5] или [-1,1] Вариант 4 1. Вычислить значение выражения при a= true и b=false: not (a and b) 2. Записать на Паскале отношение, истинное при выполнении указанного условия и ложное в противном случае: x лежит вне отрезков [2,5] и [-1,1] Вариант 5 1. Вычислить значение выражения при c=true: not (pred(c) or (ord(c)=1)) 2. Записать на Паскале отношение, истинное при выполнении указанного условия и ложное в противном случае: каждое из чисел x, y, z положительно Вариант 6 1. Вычислить значение выражения при p=q=true: (p< true)=(q= false) 2. Записать на Паскале отношение, истинное при выполнении указанного условия и ложное в противном случае: хотя бы одно из чисел x, y, z положительно Вариант 7 1. Вычислить значение выражения при a=false, b=true: a and b > a or b 2. Записать на Паскале отношение, истинное при выполнении указанного условия и ложное в противном случае: ни одно из чисел x, y, z не является положительным 19 Вариант 8 1. Если a=true и x=1, то какое значение получит логическая переменная d после присваивания d:= not a or odd(x) ? 2. Нарисовать область, в которой истинно выражение: (abs(x)<=1) and (abs(y)>=1) Вариант 9 1. Если a=true и x=1, то какое значение получит логическая переменная d после присваивания d:= ord(a) <> x ? 2. Нарисовать область, в которой истинно выражение: (sqr(x)+sqr(y)<=4) and (y<=x) Вариант 10 1. Написать оператор присваивания, в результате которого логическая переменная t получает значение true, если выполняется указанное условие: числа x, y, z равны между собой 2. Нарисовать область, в которой истинно выражение: (y>=x) and (y+x>=0) and (y<=1) Вариант 11 1. Написать оператор присваивания, в результате которого логическая переменная t получает значение true, если выполняется указанное условие: из чисел x, y, z только два равны между собой 2. Нарисовать область, в которой истинно выражение: 2 (y>=x ) and (x>=0) and (y<=1) Вариант 12 1. Написать оператор присваивания, в результате которого логическая переменная t получает значение true, если выполняется указанное условие: p делится нацело на q (p и q натуральные числа) 2. Нарисовать область, в которой истинно выражение: (sqr(y)+sqr(x)<1) or (y>0) and (abs(x)<=1) Вариант 13 1. Вычислить значение выражения при t=true, p=101010: t and (p mod 3=0) 2. Записать выражение истинное при выполнении условия: сумма цифр двухзначного числа нечетна Вариант 14 1. Вычислить значение выражения при t=15: t mod 7= t div 5 –1 2. Записать выражение истинное при выполнении условия: точка с координатами (x,y) лежит в первой или третьей четверти координатной плоскости 20 Вариант 15 1. Вычислить значение выражения при p=0.182: odd( trunc(10*p)) 2. Записать выражение истинное при выполнении условия: цифра 5 входит в десятичную запись трехзначного натурального числа Задание 2 Задание: составить программу решения задачи. Указание к выполнению: перед написанием программы необходимо выполнить следующие этапы: 1. Определить количество необходимых переменных, их имена и тип. 2. Определить входные данные, область допустимых значений и способ их задания. 3. Определить выходные данные, формат вывода, способ вывода на экран. 4. Записать словесно по шагам ход решения задачи. 5. Определить заранее значение выходных данных при тестовых значениях входных данных. Образец выполнения задания Задача: составить программу, которая определяет, принадлежит точка с координатами (x, y) заштрихованной области или нет. y 1 -1 1 x 1. Для решения данной задачи мне понадобятся переменные x и y для хранения координат точки, которые могут принимать любые действительные значения, поэтому тип этих переменных обозначу real. 2. Переменные x и y являются входными данными. Их значение должно быть определено до начала вычислений. Ввод этих переменных буду осуществлять с клавиатуры с помощью процедуры readln(). 3. Результатом работы программы должно быть сообщение «Точка принадлежит заштрихованной области» или «Точка не принадлежит заштрихованной области». Для вывода сообщений воспользуюсь процедурой writeln(). Специальной переменной для вывода сообщения вводить не буду. 21 4. Ход решения задачи: - ввод данных x и y; - проверить условие принадлежности заштрихованной области. Для этого сначала определим с помощью системы неравенств заштрихованную область: y 0 x y 1 y x 1 Проверку условия принадлежности заштрихованной области можно сформулировать следующим образом: Если y0 и x+y1 и y-x1, то вывести на экран сообщение «Точка принадлежит заштрихованной области», иначе вывести на экран сообщение «Точка не принадлежит заштрихованной области». 5. Проверим правильность выполнения алгоритма с помощью задания тестовых значений переменных x и y. Пусть x=0, y=0.5. Эта точка заведомо принадлежит заштрихованной области. Проверяем выполнение условия принадлежности: y0 – верно; x+y1 – верно; y-x1 – верно. Все три неравенства выполняются, следовательно, условие принадлежности заштрихованной области принимает значение «истина». По правилу выполнения условного оператора будет выведено на экран сообщение, стоящее после служебного слова «то», а именно «Точка принадлежит заштрихованной области». Возьмем теперь точку, которая заведомо не принадлежит области. Пусть x=2, y=-1. Проверяем условие принадлежности: y0 – неверно; x+y1 – верно; y-x1 – верно. Т.к. одно из неравенств не выполняется, следовательно, все условие принимает значение «ложь». По правилам выполнения условного оператора будет выведено сообщение, стоящее после служебного слова «иначе», а именно «Точка не принадлежит заштрихованной области». Текст программы Program zadacha2_2; Var x,y: real; begin witeln(‘введите координаты точки x и y через пробел’); readln(x, y); if (y>=0) and (x+y<=1) and (y-x<=1) then writeln(‘Точка принадлежит области’) else writeln(‘Точка не принадлежит области’); end. 22 Дальнейшие действия: Откомпилировать программу (клавиша <F9>), исправить ошибки, допущенные при наборе. Запустить программу на исполнение (сочетание клавиш <Ctrl>+<F9>). Задать тестовые значения переменных. Посмотреть результат выполнения программы, нажав сочетание клавиш <Alt>+<F5>, оценить полученный результат. Запустить программу повторно, задать произвольные значения переменных, записать полученные результаты. Вариант 1 x 2 3x 9, если _ x 3 Для заданного x вычислить значение функции f 1 , если _ x 3 3 x 6 Вариант 2 Вычислить значение выражения, не используя стандартную функцию Abs(). y fd f d 10 Вариант 3 x 2 3x 9, если _ x 3 Для заданного x вычислить значение функции f x , если _ x 3 3 x 6 Вариант 4 Вычислить значение выражения, не используя стандартную функцию Abs(). z x 1 y x Вариант 5 9, если _ x 3 Для заданного x вычислить значение функции f 1 x 2 1 , если _ x 3 Вариант 6 Вычислить значение выражения, не используя стандартную функцию Abs(). x a b b a ab 23 Вариант 7 0, если _ x 1 Для заданного x вычислить значение функции f 1 x 6 , если _ x 1 Вариант 8 Вычислить значение выражения, не используя стандартную функцию Abs(). y x 1 x 5 x Вариант 9 x 2, если _ 0 x 3 4, если _ x 3 _ или _ x 0 Для заданного x вычислить значение функции f Вариант 10 Вычислить значение выражения, не используя стандартную функцию Abs(). c ab ab Вариант 11 x 2 4 x 5, если _ x 2 Для заданного x вычислить значение функции f 1 , елси _ x 2 2 x 4x 5 Вариант 12 Вычислить значение выражения, не используя стандартную функцию Abs(). f x y yz zx Вариант 13 sin x, если _ x 0 cos x, если _ x 0 Для заданного x вычислить значение функции f Вариант 14 Вычислить значение выражения, не используя стандартную функцию Abs(). s a b 2 c 1 Вариант 15 3 x 9, если _ x 7 Для заданного x вычислить значение функции f 1 x 7 , если _ x 7 Задание 3 24 Задание: составить программу решения задачи, используя оператор выбора. Указания к выполнению: пункты 1-5 смотри задание 2. Образец выполнения задания Задача: написать программу, которая по номеру месяца выводит название сезона. 1. Для решения задачи мне потребуется переменная, обозначающая номер месяца. Пусть эта переменная называется n. 2. Входными данными в этой задаче является переменная n. Её значение должно быть введено до начала вычислений. Ввод переменной буду осуществлять с клавиатуры. Номер месяца может принимать значения от 1 до 12, поэтому тип переменной можно описать как диапазон 1..12, или как byte. 3. В результате выполнения программы на экран должно быть выведено одно из сообщений «Зима», «Весна», «Лето», «Осень» или «Месяца с таким номером нет». Переменную для хранения сообщения вводить не буду. Сообщения буду выводить с помощью процедуры writeln(). 4. Ход решения задачи: - ввод переменной n; - выбор одного из вариантов: если n=1 или n=2 или n=12, то вывести на экран сообщение «Зима» если n=3 или n=4 или n=5, то вывести на экран сообщение «Весна» если n=6 или n=7 или n=8, то вывести на экран сообщение «Лето» если n=9 или n=10 или n=11, то вывести на экран сообщение «Осень» если не выполняется ни один из вариантов, то вывести на экран сообщение «Месяца с таким номером нет» 5. Тест для данной задачи придумайте самостоятельно и проверьте правильность решения задачи. Текст программы Program zadzcha2_3; Var n: byte; Begin Writeln(‘Введите номер месяца’); Readln (n); Case n of 1, 2, 12: writeln(‘Зима’); 3, 4, 5: writeln(‘Весна’); 6, 7, 8: writeln(‘Лето’); 9, 10, 11: writeln(‘Осень’); else writeln(‘Месяца с таким номером нет’) end; end. 25 Дальнейшие действия: смотри задание 2. Вариант 1 По заданному возрасту человека (n целое число) вывести сообщение каков возраст, добавляя к n слова «лет», «год» или «года». Например, 25 лет, 4 года, 51 год. Вариант 2 Составить программу случайного выбора места летнего отдыха из семи предлагаемых туристическим агентством курортов, причем с вероятностью 3/10 придется отдыхать на даче. Вариант 3 Составить программу, которая случайным образом выбирает один из трех вариантов: вычисление длины окружности и площади круга по заданному радиусу; вычисление периметра и площади треугольника по трем сторонам; вычисление периметра и площади параллелограмма по двум сторонам и углу между ними. Вариант 4 Составить программу случайного выбора трех дисциплин, по которым придется сдавать экзамены, из предлагаемых на выбор четырех предметов (всего возможно 4 варианта). Вариант 5 Дано натуральное число N (1N99), обозначающее количество копеек. Вывести на экран его значение в словесной форме. Например, N=35. Должно быть выведено «тридцать пять копеек». Следует учесть, что в данной фразе слова «копеек» может меняться на «копейка» или «копейки». Вариант 6 В классе учится N учеников (20N40). Вывести на экран количество учеников в классе в словесной форме, в виде « в классе учится N(словами) учеников», следует учесть, что слово «учеников» может меняться на «ученик» или «ученика». Например, N=23, должно быть выведено «в классе двадцать три ученика». Вариант 7 Составить программу случайного выбора дежурного из списка, в котором 4 мальчика и 4 девочки, причем для девочек вероятность выбора в два раза ниже, чем для мальчиков. 26 Вариант 8 Задано количество долларов (целое число), предназначенных для обмена, и курс обмена в рублях (целое число). Вывести на экран сумму, полученную в результате обмена, в рублях, добавляя в конце «рублей», «рубля» или «рубль». Например, 234 рубля, 541 рубль. Вариант 9 Из списка видеофильмов, в котором 2 триллера, 2 боевика, 2 мелодрамы и 2 комедии случайным образом выбрать «самый популярный фильм», причем вероятность того, что это будет триллер или боевик в 2 раза выше, чем для любого другого фильма. Вариант 10 Дана сумма денег в рублях (целое число), известен курс обмена рублей на доллары (целое число). Вывести на экран, сколько долларов можно приобрести на данную сумму, дописывая в конце слово «долларов», «доллара» или «доллар». Например, 10 долларов, 74 доллара и т.п. Вариант 11 Для любого трехзначного числа вывести на экран его значение в словесной форме. Например, N=204, должно быть напечатано «двести четыре» Вариант 12 Из четырех предметов, по двум из которых нужно сдавать зачет, предлагается составить список по два предмета в каждом варианте. Случайным образом выбрать из предложенного списка один из вариантов. Вариант 13 На автобусную остановку подъезжают автобусы 6 маршрутов. Составить программу, которая случайным образом выбирает из списка маршрут подъехавшего автобуса, если известно, что три маршрута из предложенного списка ходят в 2 раза чаще, чем другие три. Вариант 14 В книжном магазине продаются книги следующих жанров: фантастика, роман, детектив, классика, поэзия, учебная литература. Составить программу, которая случайным образом выбирает из списка жанр покупаемой книги, если известно, что классику и поэзию покупают в два раза реже, чем любую другую книгу. Вариант15 Для осуществления платежа вводится сумма в рублях и копейках. Составить программу, которая записывает сумму прописью в следующем виде: ________________руб. kk коп. (сумма прописью) 27 Например, вводится сумма платежа 134 руб. 45 коп, должно быть выведено «сто тридцать четыре руб. 45 коп». Задание 4 Задание: составить программу решения задачи. Указание к выполнению: выполнить все требования к лабораторной работе самостоятельно. Вариант 1 Дано число x. Напечатать в порядке возрастания sinx, cosx, lnx. Если x таково, что логарифм не существует, то вывести об этом сообщение и сравнивать оставшиеся два значения. Вариант 2 Два прямоугольника, расположенные в первом квадранте, со сторонами параллельными осям координат, заданы координатами своих левого верхнего и правого нижнего углов. Для первого прямоугольника это точки (x1, y1) и (x2, 0), для второго – (x3, y3) и (x4, 0). Определить, пересекаются ли данные прямоугольники, и вычислить площадь общей части. Вариант 3 Дано действительное число x. Вычислить значение функции f в точке x, если функция f периодическая, с периодом 1.5, совпадающая на отрезке [0, 1.5] с функцией x2-2.25x. Вариант 4 Выяснить, рубит ли шашка на поле (k,h) шашку на поле (m,n). Координаты полей задавать цифрами от 1 до 8, учитывать, что шашку, стоящую на краю доски, срубить нельзя. Вариант 5 Даны координаты двух полей шахматной доски. Выяснить, можно ли одним ходом коня с поля (k, h) попасть на поле (m, n). Вариант 6 Вводя координаты трех точек, выяснить, каким будет треугольник, построенный на этих точках, тупоугольный, остроугольный или прямоугольный. Вариант 7 Выяснить, являются ли поля (k, h) и (m, n) на шахматной доске полями одного цвета. 28 Вариант 8 Считая, что стандартная функция sinx применима только к аргументам из отрезка [0, ], вычислить значение sinx для произвольного значения x. Вариант 9 Даны числа a1, b1, c1 и a2, b2, c2. Напечатать координаты точки пересечения прямых a1x+ b1y= c1 и a2x + b2y = c2, либо сообщить, что эти прямые не пересекаются. Вариант 10 Даны произвольные числа a, b, c. Выяснить, можно ли построить треугольник с такими сторонами, если можно, то какой. Вариант 11 Даны координаты двух полей шахматной доски. Выяснить, можно ли с поля (k, h) ходом слона попасть на поле (m, n). Вариант 12 Даны три стороны одного треугольника и три стороны другого треугольника. Выяснить, являются ли треугольники подобными. Вариант 13 Считая, что стандартная функция cosx применима только к аргументам из отрезка [-/2, /2], вычислить значение cosx для произвольного значения x. Вариант 14 Даны размеры дверного проема и шкафа. Выяснить, пройдет ли шкаф через дверной проем. Шкаф можно поворачивать, наклонять нельзя. Вариант 15 Даны координаты двух полей шахматной доски. Выяснить, можно ли с поля (k, h) ходом ферзя попасть на поле (m, n). Тема: Циклические структуры. Программирование циклических алгоритмов. Циклы При решении подавляющего большинства задач (в том числе и весьма несложных) в программе практически невозможно задать в явном виде все операции, которые необходимо выполнить. В самом деле, пусть необходимо вычислить сумму первых n членов гармонического ряда: 29 Y= 1+ 1/2+ 1/3 + …+ 1/n Очевидно, что с использованием только рассмотренных выше типов операторов можно составить программу лишь для фиксированного значения n. Например, при n=5 требуемые вычисления можно задать с помощью оператора присваивания вида: Y:= 1+1/2+1/3+1/4+1/5 Если же значение n не фиксируется, а является исходным данным, вводимым в процессе выполнения программы (и даже константой, описанной в программе), то аналогичный оператор присваивания записать невозможно. Ибо запись вида Y:= 1+1/2+1/3+…+1/n в языках программирования недопустима. Для устранения возникающих трудностей служат операторы цикла. Они позволяют повторять выполнение отдельных частей программы. Можно выделить четыре цикла, присутствующих в том или ином виде во всех языках программирования: простой арифметический цикл (цикл с параметром с шагом 1), сложный арифметический цикл (цикл с параметром с произвольным шагом), итерационный цикл с предусловием, итерационный цикл с постусловием. Простой арифметический цикл (цикл с параметром) Вернемся к рассмотренной выше задаче вычисления суммы первых n членов гармонического ряда, правила которой невозможно задать в виде арифметического выражения, если значение n заранее не фиксировано. На самом деле вычисление этой суммы можно осуществить по очень простому и компактному алгоритму: предварительно положим y=0 (с помощью оператора присваивания y:=0), а затем выполним оператор присваивания y:= y+1/i для последовательных значений i= 1,2,…,n. При каждом очередном выполнении этого оператора к текущему значению y будет прибавляться очередное слагаемое. Как видно, в этом случае процесс вычислений будет носить циклический характер: оператор y:= y+1/i должен выполняться многократно, т.е. циклически, при различных значениях i. Этот пример циклического вычислительного процесса является весьма типичным; его характерные особенности состоят в том, что - число повторений цикла известно к началу его выполнения (в данном случае оно равно значению n, которое предполагается заданным к этому времени); - управление циклом осуществляется с помощью переменной порядкового типа, которая в этом циклическом процессе принимает последовательные значения от заданного начального до заданного конечного значений (в нашем случае – это целочисленная переменная i, принимающая последовательные значения от 1 до n). 30 Для компактного задания подобного рода вычислительных процессов и служит оператор цикла с параметром. Чаще всего используется следующий вид этого оператора: For V:= E1 to E2 do S, где for (для), to (увеличиваясь к) и do (выполнять, делать) – служебные слова, V – переменная порядкового типа, называемая параметром цикла, Е1 и Е2 – выражения того же типа, что и параметр цикла, S – оператор, который и выполняется многократно в цикле, называемый телом цикла. Заметим, что в Паскале после do должен стоять один оператор, если необходимо выполнить несколько действий, то они должны быть объединены в один составной оператор путем заключения в операторные скобки. Этот оператор цикла предусматривает присваивание параметру цикла V последовательных значений от начального значения, равного значению выражения Е1, до конечного значения, равного значению выражения Е2, т.е. при каждом повторении выполняется оператор присваивания V:= succ(V), и выполнение оператора S при каждом значении параметра цикла V. При этом значения выражений Е1 и Е2 вычисляются один раз, при входе в оператор цикла, а значение параметра цикла V не должно изменяться в результате выполнения оператора S. Если заданное конечное значение меньше начального значения (что допустимо), то оператор S не выполняется ни разу. В Паскале считается, что при нормальном завершении выполнения оператора цикла значение параметра цикла не определено. С использованием оператора цикла с параметром алгоритм вычисления суммы первых n членов гармонического ряда может быть задан следующим образом: Readln(n); Y:= 0; For i:= 1 to n do y:= y+1/i; В некоторых случаях бывает удобно, чтобы параметр цикла принимал последовательные, но не возрастающие, а убывающие значения. Для таких случаев в Паскале предусмотрен оператор цикла с параметром следующего вида: For V:= E1 downto E2 do S, где downto (уменьшаясь к) – служебное слово, а все остальные слова и выражения имеют прежний смысл. Изменение параметра цикла от большего значения к меньшему происходит при выполнении присваивания V:= pred(V). Заметим, что начальное значение может быть меньше конечного значения. В этом случае оператор S не выполнится ни разу. Значение параметра цикла по завершении выполнения такого цикла так же считается неопределенным. Следует запомнить и то, что для обоих вариантов записи цикла с параметром справедливо: если начальное и конечное значения равны, то тело цикла (оператор S) выполнится один раз. 31 Заметим так же, что параметр цикла может и не использоваться в теле цикла, так что основное его назначение – это управление числом повторений цикла. Например, значение y=xn, где n>=0 – целое, можно вычислить по следующему алгоритму: предварительно положить y=1, а затем n раз домножить это значение на x: Readln(n); Readln(x); Y:= 1; For i:= 1 to n do y:= y*x; Как видно, здесь параметр цикла i служит лишь для того, чтобы тело цикла (оператор y:=y*x) выполнилось нужное число раз. Арифметический цикл с произвольным шагом Естественным усложнением простого арифметического цикла является цикл, в котором параметр цикла изменяется не на 1, а на произвольную величину – шаг приращения. При этом в процессе выполнения цикла шаг изменяется по заданному закону. Стандартные операторы для реализации такого цикла есть в Форте, в других языках их приходится организовывать из простейшего арифметического цикла. Итерационные циклы Итерационные циклы отличаются от циклов с параметром тем, что в них заранее неизвестно число повторений. Пусть мы отправляемся за грибами и возвращаемся домой, когда корзина наполнится. Все грибники делятся на 2 категории: 1. Смотрят, есть ли место в корзине, а уже потом срывают грибы, если их можно поместить в корзину. (Правда, в жизни таких грибников встречать не приходилось) 2. Сначала срывают грибы, а уже потом думают, как их положить в корзину. Отсюда получаются два варианта реализации итерационных циклов: с предусловием и с постусловием. В цикле с предусловием сначала проверяется условие, а потом делается шаг. Грибник придет с полной или почти полной корзиной. В цикле с постусловием – сначала шаг, а потом проверка. Как всякий нормальный грибник, этот принесет полную или слегка переполненную корзину. Какой алгоритм выбрать? Это зависит от конкретной задачи. Если, сделав шаг без проверки, можно свалиться в яму, то лучше проверка вначале (как слепой с палочкой). Ну, а если шаг без проверки вас не пугает, то можно отложить ее до завершения шага. Нужно также проанализировать событие, которого мы ожидаем. Если оно может случиться до первого шага, то нужен цикл с предусловием. А 32 если событие не может случиться до первого шага, то нужен цикл с постусловием. Оператор цикла с постусловием Рассмотрим теперь математическую задачу. Пусть нам необходимо вычислить сумму первых членов гармонического ряда, удовлетворяющих условию 1/i>=e, где 0<e<1, а i=1,2,3…...Эту задачу можно решить по следующему алгоритму: положить предварительно y=0 и i=0, а затем в цикле увеличивать i на 1, к значению y добавлять очередное слагаемое 1/i до тех пор, пока текущее значение 1/i впервые окажется больше заданного значения 0<e<1. Очевидно, что число повторений этого цикла заранее не известно. В подобного рода случаях мы можем лишь сформулировать условие, при выполнении которого процесс добавления к сумме очередного слагаемого должен завершиться. Для задания таких вычислительных процессов в Паскале и служит оператор цикла с постусловием. Этот оператор имеет вид: Repeat S1; S2;…;Si until B, где repeat (повторять) и until (до) – служебные слова, через Si обозначен любой оператор Паскаля, а через В – логическое выражение. При выполнении этого оператора цикла последовательность операторов, находящихся между словами repeat и until, выполнится один или более раз. Этот процесс завершается, когда после очередного выполнения заданной последовательности операторов логическое выражение В примет (впервые) значение true. Таким образом, с помощью логического выражения В задается условие завершения выполнения оператора цикла. Поскольку в данном случае проверка условия производится после выполнения последовательности операторов (тела цикла), этот оператор цикла и называется оператором цикла с постусловием. С использованием этого вида оператора цикла задача о суммировании первых членов гармонического ряда, удовлетворяющих заданному условию, может быть реализована следующим образом: readln(e); i:=0; y:=0; Repeat i:=i+1; y:=y+1/i; Until 1/i<e; Заметим, что оператор цикла с постусловием является более общим, чем оператор цикла с параметром — любой циклический процесс, задаваемый с помощью цикла с параметром можно представить в виде цикла с постусловием. Обратное утверждение неверно. Например, задача о 33 суммировании первых n членов гармонического ряда, рассмотренная ранее, с оператором цикла с постусловием будет выглядеть так: Readln(n); i:=0; y:=0; Repeat i:=i+1; y:=y+1/i; Until i>n; Оператор цикла с предусловием В случае оператора цикла с постусловием входящая в него последовательность операторов заведомо будет выполняться хотя бы один раз. Между тем довольно часто встречаются такие циклические процессы, когда число повторений цикла тоже неизвестно заранее, но при некоторых значениях исходных данных предусмотренные в цикле действия вообще не должны выполняться, и даже однократное выполнение этих действий может привести к неверным или неопределенным результатам. Пусть, например, дано вещественное число М. Требуется найти наименьшее целое неотрицательное число k, при котором 3k>M. Эту задачу можно решить по следующему алгоритму: предварительно положить y=1 и k=0; затем в цикле домножать значение y на 3 и увеличивать значение k на 1 до тех пор, пока текущее значение y впервые окажется больше значения М. На первый взгляд, здесь можно воспользоваться оператором цикла с постусловием: y:=1; k:=0; Repeat y:=y*3; k:=k+1; Until y>M; Однако нетрудно убедиться в том, что при M<1 будет получен неправильный результат k=1, тогда как должно быть получено k=0: в этом случае предварительно сформированное значение k=0 является окончательным результатом и действия, предусмотренные в цикле, выполняться не должны. Для задания подобного рода вычислительных процессов, когда число повторений цикла заранее неизвестно и действия, предусмотренные в цикле, могут вообще не выполняться, и служит оператор цикла с предусловием. Этот оператор цикла имеет в Паскале следующий вид: While B do S, где while (пока), do (делать, выполнять) – служебные слова, В – логическое выражение, S – оператор. Здесь оператор S выполняется ноль или более раз, но перед каждым очередным его выполнением вычисляется значение выражения В, и оператор S выполняется только в том случае, когда значение выражения В true. Выполнение оператора цикла завершается, 34 когда выражение В впервые принимает значение false. Если это значение выражение В принимает при первом же его вычислении, то оператор S не выполнится ни разу. В рассматриваемой нами задаче правильное значение k при любом значении М может быть получено следующим образом: y:=1; k:=0; While y<=M do Begin y:=y*3; k:=k+1; End; Оператор цикла с предусловием можно считать наиболее универсальным – с использованием таких операторов можно задать и циклические процессы, определяемые операторами цикла с параметром и постусловием. Отметим отличия и особенности хорошего стиля работы с рассмотренными циклическими операторами. Цикл с предусловием Wile (пока Цикл с постусловием Repeat (до условие истинно) истинности условия) 1) До начала цикла должны быть сделаны начальные установки переменных, управляющих условием цикла, для корректного входа в цикл 2) В теле цикла должны присутствовать операторы, изменяющие переменные условия так, чтобы цикл через некоторое число итераций завершился 3) Цикл работает пока условие истинно (пока True) 3) Цикл работает пока условие ложно (пока False) 4) Цикл завершается, когда условие становится ложным (до False) 4) 5) Цикл может не выполниться ни разу, если исходное значение условия при входе в цикл False 5) Цикл обязательно выполнится как минимум один раз 6) Если в теле цикла требуется выполнить более одного оператора, то необходимо использовать составной 6) 35 Цикл завершается, когда условие становится истинным (до True) Независимо от количества операторов в теле цикла, использование составного оператора не требуется оператор Цикл со счетчиком (с параметром) For 1) Начальная установка переменной счетчика цикла до заголовка не требуется 2) Изменение в теле цикла значений переменных, стоящих в заголовке не допускается 3) Количество итераций цикла неизменно и точно определяется значениями нижней и верхней границ и шага приращения 4) Нормальный ход работы цикла может быть нарушен оператором goto или процедурами Break и Continue 5) Цикл может не выполниться ни разу, если шаг цикла будет изменять значение счетчика от нижней границы в направлении, противоположном верхней границе Оператор, который выполняется в цикле, сам может быть циклом. Это относится ко всем видам циклов. В результате мы получаем вложенные циклы. Механизм работы вложенных циклов удобнее всего рассмотреть на примере вложенных циклов с параметром. Пусть нам нужно описать работу электронных часов, начиная с момента времени 0 часов, 0 минут, 0 секунд. Значение минут станет равным 1 только после того, как секунды «пробегут» все последовательные значения от 0 до 59. Часы изменят свое значение на 1 только после того, как минуты «пробегут» все последовательные значения от 0 до 59. Таким образом, вывод всех значений времени от начала суток до конца суток может быть представлен следующим фрагментом программы: For h:=0 to 23 do For m:=0 to 59 do For s:=0 to 59 do Writeln(h,’:’,m,’:’,s); Для удобства реализации циклических структур на Паскале в последних версиях языка введены операторы break и continue, применяемые внутри циклов. Они расширяют возможности использования циклов и улучшают структуру программы. В процессе выполнения тела цикла до полного завершения цикла могут возникнуть дополнительные условия, требующие завершения цикла. В этом случае цикл может быть прекращен оператором break. 36 В ходе выполнения цикла может возникнуть условие, при котором необходимо пропустить все или некоторые действия, предусмотренные в цикле, не прекращая работу цикла совсем. Для этого используется оператор continue, который передает управление в ту точку программы, где проверяется условие продолжения или прекращения цикла. Лабораторная работа №3 Тема: Циклические структуры. Программирование циклических алгоритмов. Задание 1 Указание к выполнению: задание 1 выполняется в тетради по вариантам с необходимыми пояснениями. Вариант 1 Найти ошибки в следующем фрагменте программы: y:=0; for x:=0.1 to 0.9 do y:=y+sin(x); Вариант 2 Определить значение переменной S после выполнения следующих операторов: s:=0; i:=0; While i<5 do i:=i+1; s:=s+1/i; Вариант 3 Сколько раз будет выполняться тело цикла? k:=0; For i:=1 to k+3 do k:=k+1; Вариант 4 Найти ошибки в следующем фрагменте программы: k:=81; y:=1; for i:=1 to sqrt(k) do y:=y*2; Вариант 5 Определить значение переменной S после выполнения следующих операторов: s:=0; i:=1; While i>1 do begin s:=s+1/i; i:=i-1 end; 37 Вариант 6 Сколько раз будет выполняться тело цикла? p:=4; repeat p:=p*0.1 until p<0.0001; Вариант 7 Найти ошибки в следующем фрагменте программы: k:=0; for i:=1 to 9 do k:=k+sqr(i); k:=k*i; Вариант 8 Определить значение переменной операторов: s:=0; n:=10; For i:=2 to n do s:=s+100 div i; S после выполнения следующих Вариант 9 Сколько раз будет выполняться тело цикла? k:=r; s:=0; For i:=k to r do s:=s+sqr(i); Вариант 10 Найти ошибки в следующем фрагменте программы: k:=1; for i:=1 to 64 do begin i:=i*2; k:=k+i end; Вариант 11 Определить значение переменной S после выполнения следующих операторов: s:=1; n:=1; For i:=2 to n do s:=s+1/i; Вариант 12 Сколько раз будет выполняться тело цикла? a:=1; b:=1; while a+b<8 do begin a:=a+1; b:=b+2 end; Вариант 13 Найти ошибки в следующем фрагменте программы: a:=1; b:=3; h:=0.2; for x:=a to b do begin writeln(x, sin(x)); x:=x+h end; Вариант 14 Определить значение переменной S после выполнения следующих операторов: s:=0; i:=1; repeat s:=s+ i mod 3; i:=i+1; until i>=7; 38 Вариант 15 Сколько раз будет выполняться тело цикла? k:=5; r:=15; for i:=k+1 to r-1 do writeln(i); Задание 2 Задание: составить программу решения задачи. Указание к выполнению: см. предыдущую лабораторную работу. Образец выполнения задания Задача: вычислить сумму членов гармонического ряда с общим членом an=1/n, превышающих заданное число (0<<1). 1. Для решения данной задачи мне потребуются следующие переменные: E для хранения заданного числа, меньшего 1, тип этой переменной real; S для вычисления суммы, т.к. суммировать будем дроби, то тип этой переменной будет real; N для обозначения знаменателя очередного слагаемого, эта переменная будет принимать только натуральные значения, поэтому ее тип определим как word. 2. Переменная E является входной переменной, ее значение должно быть определено до начала вычислений. Ввод переменной буду производить с клавиатуры. 3. В результате выполнения программы на экран должно быть выведено значение переменной S. 4. Ход решения задачи: - ввод значения E - зададим начальные значения S=0 и N=1 - т.к. мы заранее не знаем сколько слагаемых нужно суммировать, то организуем цикл по условию. Пока 1/N>E повторяем следующие действия: а) к сумме прибавляем очередное слагаемое S:=S+1/N; б) увеличиваем значение знаменателя на единицу N:=N+1 - вывод значения переменной S 5. Проверим правильность составленного алгоритма решения задачи для тестового значения E=0.3. Проследим ход решения задачи: - начальные значения S=0, N=1 - проверяем условие выполнения цикла: 1/1>0.3 ? Да. Значит, выполняем следующие действия: а) S=S+1/N=0+1/1=1 б) увеличиваем знаменатель на 1 N=N+1=1+1=2 - снова проверяем условие выполнения цикла: 1/2>0.3 ? Да. Значит, выполняем следующие действия: а) S=S+1/N=1+1/2=1.5 б) увеличиваем знаменатель на 1 N=N+1=2+1=3 - снова проверяем условие выполнения цикла: 1/3>0.3 ? Да. Значит, выполняем следующие действия: а) 39 - S=S+1/N=1.5+1/3=1.83333 б) увеличиваем знаменатель на 1 N=N+1=3+1=4 снова проверяем условие выполнения цикла: 1/4>0.3 ? Нет. Значит, прекращаем выполнение цикла В результате выполнения программы должно быть напечатано значение 1.8333333. Текст программы Program zadacha3_2; Var E,s: real; N: word; Begin Writeln (‘введите Е’); Readln (E); S:=0; N:=1; While 1/n>E do Begin {так как в цикле должны выполняться два оператора, то их нужно заключить в операторные скобки} S:=S+1/n; N:=n+1; End; {конец тела цикла} Writeln(‘искомая сумма S=’, S) End. Дальнейшие действия: настало время научиться трассировать программу, т.е. выполнять ее в пошаговом режиме и следить за изменением значений переменных (читай Приложение, стр.50). Откомпилировать программу, исправить ошибки, допущенные при наборе; Провести пошаговое выполнение программы для тестовых значений входных данных с отслеживанием значений переменных. В нашей задаче будем следить за изменением значений переменных N, S и выражением 1/N>E. Для этого откроем окно Watches по команде Watch меню Debug. Нажмем сочетание клавиш <Ctrl>+<F7> и в диалоговом окне напишем имя переменной N. Повторно нажмем <Ctrl>+<F7> и запишем имя переменной S. Еще раз нажмем <Ctrl>+<F7> и введем выражение 1/N>E. Запустим программу для пошагового выполнения, нажав <F8> (<F7>). В окне Watches будем наблюдать, как меняются значения переменных и выражения, одновременно в верхней части экрана будет подсвечиваться очередная команда. Результаты трассировки программы следует записать в тетрадь. После проверки и отладки окно Watches можно закрыть, нажав <Alt>+<F3>. 40 Запустить программу на выполнение в обычном режиме, задать произвольные допустимые значения входных данных. Записать результат. Вариант 1 Найти наименьший номер последовательности, для которого выполняется условие |an - an-1|<. Вывести на экран этот номер и все элементы ai, где i=1, 2, 3, ...,n, если =10-3. an= arctg an-1+1, a1=0. Вариант 2 Найти наименьший номер последовательности, для которого выполняется условие |an - an-1|<. Вывести на экран этот номер и все элементы ai, где i=1, 2, 3, ...,n, если =10-3. an 2 1 , a1=2. an 1 Вариант 3 Найти наименьший номер последовательности, для которого выполняется условие |an - an-1|<. Вывести на экран этот номер и все элементы ai, где i=1, 1 2 2, 3, ...,n, если =10-3. an tgan 1 , a1=0.5. Вариант 4 Найти наименьший номер последовательности, для которого выполняется условие |an - an-1|<. Вывести на экран этот номер и все элементы ai, где i=1, 1 2 2, 3, ...,n, если =10-3. an cos an 1 , а1=0.5. Вариант 5 Найти наименьший номер последовательности, для которого выполняется условие М. Вывести на экран этот номер и все элементы ai, где i=1, 2, 3, 1 2 ...,n. an (an 1 2 an 1 ), a1 2, M : an2 2 Вариант 6 Дан числовой ряд и малая величина . Найти сумму ряда с точностью , общий член которого задан формулой: an 2n 1 . 2n Вариант 7 Найти наименьший номер последовательности, для которого выполняется условие |an - an-1|<. Вывести на экран этот номер и все элементы ai, где i=1, 2 an21 , a1 2 2, 3, ...,n, если =10 . an 2an 1 -3 41 Вариант 8 Дан числовой ряд и малая величина . Найти сумму ряда с точностью , общий член которого задан формулой: an 1 1 n. n 2 3 Вариант 9 Найти наименьший номер последовательности, для которого выполняется условие М. Вывести на экран этот номер и все элементы ai, где i=1, 2, 3, (1) n ...,n. an n , М: |аn|<. 2 Вариант 10 Найти наименьший номер последовательности, для которого выполняется условие |an - an-1|<. Вывести на экран этот номер и все элементы ai, где i=1, 2, 3, ...,n, если =10-3. an an 1 an 2 , a1 1, a2 2 2 Вариант 11 Найти наименьший номер последовательности, для которого выполняется условие |an - an-1|<. Вывести на экран этот номер и все элементы ai, где i=1, 2, 3, ...,n, если =10-3. an e a , a1 0 . Вариант 12 Найти наименьший номер последовательности, для которого выполняется условие |an-an-1|<. Вывести на экран этот номер и все элементы ai, где i=1, 2, n 1 3, ...,n, если =10-3. an x , a1 x . 2 an21 Вариант 13 Найти наименьший номер последовательности, для которого выполняется условие М. Вывести на экран этот номер и все элементы ai, где i=1, 2, 3, ...,n. an (1) n 2n , M :| an | n! Вариант 14 Дан числовой ряд и малая величина . Найти сумму ряда с точностью , общий член которого задан формулой: an 2n . (n 1)! Вариант 15 Найти наименьший номер последовательности, для которого выполняется условие М. Вывести на экран этот номер и все элементы ai, где i=1, 2, 3,...n. an 1 , M : an (n 1) 2 42 Задание 3 Задание: составить программу вычисления функции F(x) на отрезке [a, b] с шагом h. Результат представить в виде таблицы, первый столбец которой – значения аргумента, второй – соответствующие значения функции. Указания к выполнению: см. предыдущую лабораторную работу. Образец выполнения задания Задача: вычислить значения функции F(x)=x + sinx на отрезке [a, b] с шагом h. Результат вывести в виде таблицы. 1. Для решения данной задачи мне потребуются следующие переменные: переменная a для задания начала отрезка, эта переменная может принимать любые вещественные значения, т.к. функция определена на всей числовой оси, поэтому тип этой переменной real; переменная b для задания конца отрезка, тип переменной real; переменная h для задания шага приращения аргумента, тип переменной real; переменные x, f для вычисления значения аргумента и соответствующего значения функции, тип переменных real; переменная n для вычисления количества точек на отрезке, может принимать натуральные значения, поэтому тип ее определим как byte; переменная i для организации цикла, эта переменная будет обозначать номер очередной точки, тип этой переменной определим как byte. 2. Входными данными в этой задаче являются концы отрезка и шаг приращения, т.е. переменные a, b, h, поэтому их значения нужно ввести до начала вычислений. Ввод буду осуществлять с клавиатуры. 3. В результате выполнения программы на экране должна быть выведена таблица значений аргумента, начиная с точки a, и соответствующих значений функции. В данной задаче целесообразно задать формат вывода значений переменных x, f, чтобы таблица выглядела красиво. Пусть общая длина переменной x будет 6 позиций, число знаков после запятой – 3, а для переменной f общая длина будет 8 позиций, число знаков после запятой – 4. В этом случае процедура вывода на экран запишется writeln(x: 6: 3, f: 8: 4). 4. Ход решения задачи: - ввод значений a, b, h - вычислим количество точек на отрезке, в которых нужно посчитать значение функции, по формуле n trunc((b a) h) - т.к. нумерация точек на отрезке начинается с 0, то организуем цикл с параметром i, в котором будем последовательно изменять его значения от 0 до n и для каждого значения i выполнять следующие действия: а) вычисляем значение аргумента x=a+i*h; б) вычисляем значение функции в точке x 43 по формуле f= x + sin(x); в) печатаем значения x и f (действия а), б), в) образуют тело цикла, при написании программы их нужно заключить в операторные скобки begin end). 5. Зададим тестовые значения. Пусть a=0, b=1, h=0.2. В результате выполнения программы на экране должна быть выведена таблица следующего вида: 0.0 0.0 0.2 0.2035 0.4 0.4070 0.6 0.6105 0.8 0.8140 1.0 1.0175 Текст программы: напишите самостоятельно. Дальнейшие действия: см. предыдущую лабораторную работу. Вариант 1 f ( x) sin x tgx Вариант 11 f ( x) sin 2 x Вариант 6 Вариант 2 1 f ( x) x cos 2 x f ( x) 2tg x 1 2 f ( x) x cos x Вариант 12 f ( x) tg 2 x 3 Вариант 7 f ( x) cos x ctgx Вариант 13 Вариант 3 f ( x) sin x cos x f ( x) tgx Вариант 8 f ( x) x cos 2 x Вариант 14 Вариант 4 f ( x) sin x 0.5 cos x Вариант 9 f ( x) cos 2 x Вариант 15 f ( x) 2 sin x 1 2 Вариант 10 Вариант 5 f ( x) 2 cos x 0.5 f ( x) sin x cos 2 x 2 Задание 4 Задание: составить программу решения задачи. Указания к выполнению: самостоятельно выполнить все требования к лабораторной работе. 44 Вариант 1 Натуральное число называется совершенным, если оно равно сумме всех своих делителей, включая единицу, но исключая себя. Напечатать все совершенные числа, меньшие заданного числа N. Вариант 2 Найти все натуральные числа, не превосходящие заданного n, которые делятся на каждую свою цифру. Вариант 3 Последовательность Хэмминга образуют натуральные числа, не имеющие других простых делителей, кроме 2, 3, 5. Найти первые N элементов этой последовательности. Вариант 4 Найти натуральное число в диапазоне от 1 до n с максимальной суммой делителей. Вариант 5 Дано целое число n>2. Напечатать все простые числа из диапазона от 2 до n. Вариант 6 Разложить целое число N на простые множители. Вариант 7 Найти сумму цифр заданного натурального числа. Вариант 8 Найти все натуральные числа, не превосходящие заданного представимые в виде суммы квадратов двух натуральных чисел. N, Вариант 9 Напечатать все различные разбиения числа N на три натуральных слагаемых. Вариант 10 Найти наименьшее натуральное число, которое можно представить суммой трех квадратов натуральных чисел не единственным образом. Вариант 11 Напечатать все простые несократимые дроби, заключенные между 0 и 1, знаменатели которых не превышают 7, в порядке возрастания. 45 Вариант 12 Последовательность Хэмминга образуют натуральные числа, не имеющие других простых делителей, кроме 2, 3, 5. Найти N-ый элемент последовательности. Вариант 13 Найти N первых простых чисел. Вариант 14 Напечатать все простые делители заданного натурального числа. Вариант 15 Найти сумму первой и последней цифры в записи натурального числа. Приложение: работа в среде программирования Паскаль Главное меню Главное меню имеет 10 пунктов. Для того, чтобы поместить курсор в главное меню, можно воспользоваться мышью или нажать клавишу F10. Пунктами главного меню являются: - File – содержит команды для работы с файлами (создание нового файла, открытие файла, сохранение файла, печать файла, работа с каталогами); - Edit – содержит команды для редактирования текста программы (копирование, удаление, перенос частей текста и др.); - Search – содержит инструменты поиска нужного текста, замены слов и др.; - Run – содержит команды, позволяющие запустить программу в различных режимах; - Compile – содержит команды, задающие режимы компиляции программ; 46 - Debug – инструменты отладки; Tools – инструменты среды; Options – опции настройки среды; Windows – команды работы с окнами; Help – справочная система. Работа с окнами Каждый файл располагается в своем окне. Окно – ограниченная область экрана, которую можно передвигать, увеличивать, закрывать и открывать. Можно открывать любое количество окон, но активным является только одно окно, в котором располагается курсор. При открытии нескольких файлов, они загружаются в окна, которые накладываются одно на другое. Активное окно располагается сверху. Все команды для работы с окнами находятся в опции Windows главного меню. - Чтобы перейти из одного окна в окно с номером N, необходимо воспользоваться комбинацией клавиш <Alt>+N, где N – номер окна. - Чтобы посмотреть список открытых окон, можно воспользоваться комбинацией клавиш <Alt>+0 или командой List меню Windows. - Чтобы закрыть окно, можно воспользоваться комбинацией клавиш <Alt>+<F3> или командой Close меню Windows. Для закрытия всех окон нужно выбрать команду Close all меню Windows. - Чтобы видеть одновременно последовательность открытых окон, т.е. расположить их каскадом, нужно выполнить команду Cascade из меню Windows. При этом, чтобы сделать активным любое окно, нужно щелкнуть левой кнопкой мыши по любой видимой части окна или нажать сочетание клавиш <Alt>+N, где N – номер окна. - Чтобы перейти к следующему окну в списке, нужно нажать клавишу <F6>, при этом окна не закрываются. Редактирование текста программы Написание программы осуществляется в редакторе. Редактирование текста программы осуществляется в основном стандартными средствами. В качестве дополнительных средств редактирования следует запомнить команды опции Edit главного меню: - Undo – отменяет последнее действие в редактировании программы; - Redo – восстанавливает действие, отмененное командой Undo; - Cut – удаляет из текста выделенный фрагмент с сохранением этого текста в специальном буфере; - Copy – копирует в буфер выделенный фрагмент текста; - Paste – вставляет из буфера текст, сохраненный командами Cut или Copy. 47 Чтобы выделить фрагмент текста программы, нужно удерживая клавишу <Shift> перемещать курсор клавишами управления . Чтобы снять выделение, нужно воспользоваться сочетанием клавиш <Ctrl>+K затем H. Чтобы удалить выделенный фрагмент без копирования в буфер, нужно воспользоваться сочетанием клавиш <Ctrl>+<delete>. Чтобы удалить строку целиком, нужно установить курсор в ее начало и нажать клавиши <Ctrl>+Y. Пошаговое выполнение программы При выполнении программы нередко возникает ситуация, когда ее работа не соответствует решению задачи. В этих случаях требуется проследить выполнение программы по шагам. Такая возможность есть. Включить режим пошагового выполнения программы можно двумя командами меню Run: Step over (или клавиша <F8>) запускает построчное выполнение программы без захода в подпрограммы; Trace into (или клавиша <F7>) запускает построчное выполнение программы с заходом в подпрограммы. Пока вы не начали использовать в своих программах процедуры и функции, обе эти команды будут работать одинаково. Каждый раз при нажатии клавиши <F8> (<F7>) будет выполняться одна строка программы и подсвечиваться очередная программная строка, чтобы продолжить пошаговое выполнение нужно снова нажать <F8> (<F7>). Чтобы прервать отладку программы, нужно выполнить команду Program reset из меню Run. Чтобы выполнить часть программы до позиции, где стоит курсор, нужно выполнить команду Go to cursor из меню Run. Обычно не достаточно выполнить пошаговое выполнение программы, чтобы выявить все ошибки в ее работе. Как правило, при пошаговом выполнении программы нужно знать, как изменяются значения переменных. Одновременное пошаговое выполнение программы и отслеживание значений переменных называется трассировкой программы. Следить за изменением значений переменных можно в специальном окне Watches. - Чтобы активизировать окно Watches, нужно выполнить команду Watch из меню Debug. - Чтобы ввести в окно Watches переменную, значение которой мы хотим проследить, нужно выполнить команду Add watch из меню Debug или нажать сочетание клавиш <Ctrl>+<F7>, после чего откроется диалоговое окно и попросит ввести имя переменной. В процессе выполнения программы текущее значение отслеживаемой переменной будет выводиться в окне Watches. Можно отследить, как изменяется значение не одной, а нескольких переменных или выражений. Для добавления переменной или выражения, значение 48 которого мы хотим проследить, к списку нужно еще раз выполнить команду Add watch (или нажать клавиши <Ctrl>+<F7>). Как посмотреть результат выполнения программы? Мы уже выяснили, что написание текста программы производится в специальном редакторе. Когда вы запускаете программу, то вывод результатов осуществляется в пользовательском окне, а затем происходит возврат в редактор, и вы опять увидите текст программы. Причем этот процесс происходит очень быстро, невозможно увидеть, что вывела программа, записать результаты. Иногда создается впечатление, что программа вообще ничего не сделала. Чтобы посмотреть результаты работы программы (это важно!), нужно выполнить команду User screen из меню Debug или нажать сочетание клавиш <Alt>+<F5>. Возврат в редактор к тексту программы осуществляется по нажатию любой клавиши. Существует возможность одновременно наблюдать на экране текст программы и результаты ее работы, для этого надо выполнить команду Output меню Debug. По этой команде открывается дополнительное окно, в которое будут выводиться результаты работы программы. Закрыть это окно можно нажатием клавиш <Alt>+<F3>. Литература 1. Абрамов В.Г., Трифонов Н.П., Трифонова Г.Н. Введение в язык Паскаль/ Учебное пособие. – М.: Наука, 1988. 2. Грызлов В.И., Грызлова Т.П. Турбо Паскаль 7.0. – М.: ДМК, 1998. 3. Фаронов В.В. Турбо Паскаль 7.0. Начальный курс/ Учебное пособие. – М.: «Нолидж», 1997. 4. Бондарев В.М., Рублинецкий В.И., Качко Е.Г. Основы программирования. – Харьков: Фолио; Ростов н/Д: Феникс, 1998. 5. Толстых Г.Д. Циклические структуры в информатике. – Информатика и образование, №7, 1997. 6. Марченко А.И., Марченко Л.А. Программирование в среде Turbo Pascal 7.0/ Под ред. Тарасенко В.П. – 5-е изд., доп. и перераб. – К.: ВЕК+, 1999. 7. Пильщиков В.Н. Сборник упражнений по языку Паскаль: учеб. пособие для вузов. – М.: Наука, 1989. 8. Информатика. Задачник-практикум в 2т./ Под ред. И.Г. Семакина, Е.К. Хеннера: Том 1. – М.: Лаборатория Базовых Знаний, 1999. 9. Бабушкина И.А., Бушмелева Н.А., Окулов С.М., Черных С.Ю. Практикум по Турбо Паскалю. Учебное пособие по курсам 49 «Информатика и вычислительная техника», «Основы программирования». – Москва, АБФ, 1998. 10. Румянцев Дмитрий, Монастырский Леонид. Путь программиста: Опыт созидания личности программиста. – М.: «Издательский Дом ИНФРАМ», 2000 11. Звягина А.С. Языки и методы программирования: средства описания данных, средства описания действий. Учебный курс. – Хабаровск: Изд-во ХГПУ, 2000. Содержание Основные этапы проектирования программ Тема: Числовые типы данных. Выражения. функции. Решение задач линейной структуры Числовые типы Выражения и операторы действий Ввод и вывод данных Лабораторная работа №1 1 Стандартные 3 6 9 9 Тема: Логические выражения. Логический тип. Условный оператор. Оператор выбора. Программирование разветвляющихся алгоритмов Логические выражения 16 Логический тип 17 Условный оператор 18 Оператор выбора 19 Лабораторная работа №2 21 50 Тема: Циклические структуры. Программирование циклических алгоритмов Циклы 32 Простой арифметический цикл (цикл с параметром) 33 Арифметический цикл с произвольным шагом 34 Итерационные циклы 35 Оператор цикла с постусловием 35 Оператор цикла с предусловием 36 Лабораторная работа №3 39 Приложение: работа в среде программирования Паскаль Главное меню Работа с окнами Редактирование текста программы Пошаговое выполнение программы Как посмотреть результат выполнения программы? Литература 51 49 49 50 50 51 52