Лекция Соболевой

Вид материалаЛекция

Содержание


Эквивалентность типов
Преобразование типов
Разбор программы
1.3. Логический тип. Ветвления. Оператор условного перехода. Полная и сокращённая форма условного оператора. Составные условия
Логические выражения
Оператор ветвления
Общее описание
Виды условных инструкций
Условный оператор
Условный оператор с одной ветвью
Условный оператор с двумя ветвями
Условный оператор с несколькими условиями
Реализация в Pascal
1.4 Символьный тип и функции для обработки символьного типа. Перевод символьного представления числа в целый тип.
1.5 Оператор выбора
1.6. Операторы цикла. Оператор цикла с предусловием. Оператор цикла с постусловием. Оператор цикла с параметром
Виды циклов
Цикл с предусловием
Цикл с постусловием
Цикл cо счётчиком (с параметром)
...
Полное содержание
Подобный материал:
1   2   3   4   5   6   7   8

Эквивалентность типов


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

Большинство реализаций языка Си используют схему структурной эквивалентности типов. Однако в книге (Ritche, D.M. 1980/ The C Programming Language - Reference Manual/ AT&T Bell Laboratories, Murray Hill, N.J. 07974) вопрос об эквивалентности типов игнорируется, и при каждой реализации может быть выбрана своя схема определения эквивалентности типов. Следовательно, вполне возможно, что результаты правильно работающей программы станут неверными при замене компилятора!

Преобразование типов


В операторах и выражениях должны использоваться переменные и константы только одного типа. Если все же мы смешиваем типы в одном выражении, то компилятор с языка Си не считает программу неправильной, как это произошло бы при программировании на языке Паскаль. Вместо этого компилятор использует набор правил для автоматического преобразования типов. Это очень удобно, но может оказаться и опасным, особенно если мы допустили смешение типов нечаянно. Приведем несколько основных правил, касающихся преобразования типов:
  1. Если операция выполняется над данными двух различных типов, обе величины приводятся к высшему из двух типов. Этот процесс называется повышением типа.
  2. Последовательность имен типов, упорядоченных от высшего типа к низшему, выглядит так: double, float, long, int, short, char. Применение ключевого слова unsigned повышает ранг соответствующего типа данных со знаком.
  3. В операторе присваивания конечный результат вычисления выражения в правой части приводится к типу переменной, которой должно быть присвоено это значение. Данный процесс может привести к повышению типа, как описано выше, или к понижению, при котором величина приводится к типу данных, имеющему более низкий приоритет.

Повышение типа обычно происходит гладко, в то время как понижение может привести к затруднениям. Причина этого проста: все число целиком может не поместиться в элементе данных низшего типа. Переменная типа char может иметь целое значение 101, но не 22225.

Пример, приведенный ниже, иллюстрирует применение этих правил:

/*преобразования*/

int main( )

{

char ch;

int i;

float f1;

f1=i=ch='A'; /***8***/

printf("ch=%c,i=%d,f1=%2.2f\n",ch,i,f1);

ch=ch+1; /***10***/

i=f1=f1+2*ch; /***11***/

f1=2.0*ch+i; /***12***/

printf("ch=%c,i=%d,f1=%2.2f\n",ch,i,f1);

ch=2.0e30;/***14***/

printf("Теперь ch=%c\n",ch);

}

Выполнив программу "преобразования", получим следующие результаты:

ch=A,i=65,f1=65.00

ch=B,i=197,f1=329.00

Теперь ch=

Разбор программы


Строки 8 и 9: величина 'A' присваивается символьной переменной ch. Переменная i получает целое значение, являющееся преобразованием символа 'A' в целое число, т.е. 65. Переменная f1 получает значение 65.00, являющееся преобразованием числа 65 в число с плавающей точкой.

Строки 10 и 13: значение символьной переменной 'A' преобразуется в целое число 65, к которому затем добавляется 1. После этого получившееся в результате число 66 преобразуется в код символа В и помещается в переменную ch.

Строки 11 и 13: при умножении на 2 значение переменной ch преобразуется в целое число 66. При сложении с величиной переменной f1 получившееся в результате число 132 преобразуется в число с плавающей точкой. Результат 197.00 преобразуется в число целого типа и присваивается переменной i.

Строки 12 и 13: перед умножением на 2.0 значение переменной ch('B') преобразуется в число с плавающей точкой. Перед выполнением сложения величина переменной i(197) преобразуется в число с плавающей точкой, а результат 329.00 присваивается переменной f1.

Строки 14 и 15: здесь производится попытка осуществить преобразование типов в порядке убывания старшинства - переменная ch полагается равной сравнительно большому числу. Результаты оказываются неутешительными. Независимо от переполнения и усечения, которые имеют место, в итоге мы получили код, соответствующий какому-то непечатаемому знаку.

Существует еще один вид преобразования типов. Для сохранения точности вычислений при арифметических операциях все величины типа float преобразуются в данные типа double. Это существенно уменьшает ошибку округления. Конечный результат преобразуется обратно в число типа float, если это диктуется соответствующим оператором описания.


1.3. Логический тип. Ветвления. Оператор условного перехода. Полная и сокращённая форма условного оператора. Составные условия


Логические типы данных Pascal-Паскаль


В Турбо Паскале логический тип данных носит название BOOLEAN. Значением логического типа может быть одна из двух констант FALSE (ложь) или TRUE (истина). Для них справедливы правила:

Ord(false)=0

Ord(true)=1

False
Succ(false)=true

Pred(true)=false


Логические переменные должны быть описаны предложением:

Var <имя_переменной>: boolean;


Величины логического типа данных можно присваивать, выводить, но нельзя вводить процедурой read.


Пример переменных с булевым значением:

X:=true;

y:=5>3


Логические выражения (условия) – это выражения, которые могут принимать лишь одно из двух значений: true (истина) или false (ложь). Для построения логических выражений используются операции отношения, которые обозначаются знаками: = (отношение на равенство), <> (отношение на неравенство), < (отношение меньше), > (отношение больше), <= (отношение меньше или равно), >= (отношение больше или равно).


Сложные условия составляются из простых с помощью логических операций: and (логическое «И»), or (логическое «ИЛИ») и not (логическое «НЕ»). При составлении сложных условий операнды логического выражения берутся в скобки (это важно!).


Пример логических выражений:

5>3;

2<=6;

(x<2)and(x>=0)

2*x+5<>0


При вычислении логических выражений операции выполняются в следующем порядке: not, and, or, операции отношения, арифметические операции. Если порядок выполнения операций нужно изменить, то применяют скобки.


Оператор ветвления (условная инструкция, условный оператор) — оператор, конструкция языка программирования, обеспечивающая выполнение определённой команды (набора команд) только при условии истинности некоторого логического выражения, либо выполнение одной из нескольких команд (наборов команд) в зависимости от значения некоторого выражения.


Общее описание


Оператор ветвления применяется в случаях, когда выполнение или невыполнение некоторого набора команд должно зависеть от выполнения или невыполнения некоторого условия. Ветвление - одна из трёх (наряду с последовательным исполнением команд и циклом) базовых конструкций структурного программирования.


Виды условных инструкций


Существует две основные формы условной инструкции, встречающиеся в реальных языках программирования: условный оператор (оператор if) и оператор многозначного выбора (переключатель, case, switch).


Условный оператор


Условный оператор реализует выполнение определённых команд при условии, что некоторое логическое выражение (условие) принимает значение «истина» true. В большинстве языков программирования условный оператор начинается с ключевого слова if.


Встречаются следующие формы условного оператора:


Условный оператор с одной ветвью


if условие then команды end

При выполнении такого оператора вычисляется условие, и если оно истинно, то выполняются команды до ключевого слова end, в противном случае выполнение программы продолжается со следующей за условным оператором команды. В языках низкого уровня (ассемблерах) это — единственная доступная форма условного оператора. В некоторых языках для условного оператора с одной ветвью используется специальное ключевое слово (обычно это when).


Условный оператор с двумя ветвями


if условие then команды1 else команды2 end

Здесь при истинности условия выполняются команды1 при ложности — команды2. При необходимости проверить последовательно несколько условий возможно каскадирование условных операторов:

if условие1

then команды1

else if условие2 then команды2

else if условие3 then команды3

...

else if условиеN-1 then командыN-1

else командыN end;


В этом случае условия будут проверяться последовательно, и как только встретится истинное, будет выполнен соответствующий набор команд и исполнение перейдёт к команде, следующей за условным оператором. Если ни одно из условий не окажется истинным, выполнятся командыN из ветви else.


Условный оператор с несколькими условиями


Вышеприведённая схема каскада условных операторов используется достаточно часто, поэтому ряд языков программирования содержит специальную конструкцию для неё, позволяющую записать множественное ветвление несколько компактнее и менее подверженную ошибкам написания:

if условие1 then команды1

else if условие2 then команды2

...

else командыN end;


порядок выполнения этого оператора в точности соответствует вышеприведённому каскаду простых операторов if-then-else.


Реализация в Pascal


Паскаль унаследовал от Алгола-60 синтаксис, согласно которому в ветвях условного оператора может быть помещена только одна команда. Поэтому для размещения там большего количества команд они группируются в составной оператор с помощью пары ключевых слов begin и end. Ветвь else в условном операторе не является обязательной. begin и end ставится только если несколько операторов, если же оператор 1, то их желательно не ставить.

If условие Then

begin

операторы;

end

else

begin

операторы;

end;


1.4 Символьный тип и функции для обработки символьного типа. Перевод символьного представления числа в целый тип.


Символьный тип. CHAR – занимает 1 байт. Значением символьного типа является множество всех символов ПК. Каждому символу присваивается целое число в диапозоне 0…255. Это число служит кодом внутреннего представления символа.


Для кодировки используется код ASCII (American Standart Code for Information Interchange – американский стандартный код для обмена информацией). Это 7-битный код, т.е. с его помощью можно закодировать лишь 128 символов в диапазоне от 0 до 127. В то же время в 8-битном байте, отведенном для хранения символа в Турбо Паскале, можно закодировать в два раза больше символов в диапазоне от 0 до 255. Первая половина символов ПК с кодами 0…127 соответствует стандарту ASCII. Вторая половина символов с кодами 128ююю255 не ограничена жёсткими рамками стандарта и может меняться на ПК разных типов.


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

СИМВОЛЬНЫЙ тип (Char) определяет упорядоченную совокупность символов, допустимых в данной ЭВМ. Значение символьной переменной или

константы - это один символ из допустимого набора.

Символьная константа может записываться в тексте программы тремя

способами:

-как один символ, заключенный в апострофы, например:

'A' 'a' 'Ю' 'ю';

-с помощью конструкции вида #K, где K - код соответствующего символа, при этом значение K должно находиться в пределах 0..255;

-с помощью конструкции вида C, где C - код соответствующего управляющего символа, при этом значение C должно быть на 64 больше

кода управляющего символа.

К величинам символьного типа применимы все операции отношения.

Для величин символьного типа определены две функции преобразования

Ord(C) Chr(K).

Первая функция определяет порядковый номер символа С в наборе символов, вторая определяет по порядковому номеру К символ, стоящий на

К-ом месте в наборе символов. Порядковый номер имеет целый тип.

К аргументам символьного типа применяются функции, которые определяют предыдущий и последующий символы:

Pred(C) Succ(C). Pred('F') = 'E' ; Succ('Y') = 'Z' .

При отсутствии предыдущего или последующего символов значение соответствующих функций не определено.

Для литер из интервала 'a'..'z' применима функция UpCase(C), кото-

рая переводит эти литеры в верхний регистр 'A'..'Z'.


VAL(ST, X, CODE) – процедура; преобразует строку символов ST во внутреннее представление целой или вещественной переменной X, которое определяется типом этой переменной; параметр CODE содержит ноль, если преобразование прошло успешно, и тогда в X помещается результат преобразований, в противном случае он содержит номер позиции в строке ST, где обнаружен ошибочный символ, и в этом случае содержимое Х не меняется; в строке ST могут быть ведущие пробелы, однако ведомые пробелы недопустимы; например, обращение val (’ 123′,k,i) пройдет успешно: k получит значений 123, в i будет помещен 0, в то время как обращение val (’ 123 ‘ , k, i) будет ошибочным: значение k не изменится, a i будет содержать 4.

Функция ORD.


1.5 Оператор выбора

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

Структура оператора выбора такова:

CASE <ключ_выбора> OF <список_выбора> [ELSE <операторы>] END

Здесь CASE, OF, ELSE, END - зарезервированные слова (случай, из, иначе, конец);

<ключ_выбора> - ключ выбора;

<список_выбора> - одна или более конструкций вида:

<константа_выбора> : <оператор>;

<константа_выбора> - константа того же типа, что и выражение<ключ_выбopa> ;

<операторы> - произвольные операторы Турбо Паскаля.

Оператор выбора работает следующим образом. Вначале вычисляется значение выражения <ключ_выбора>, а затем в последовательности операторов <список_выбора> отыскивается такой, которому предшествует константа, равная вычисленному значению. Найденный оператор выполняется, после чего оператор выбора завершает свою работу.

Если в списке выбора не будет найдена константа, соответствующая вычисленному значению ключа выбора, управление передается операторам, стоящим за словом ELSE. Часть ELSE <оператор> можно опускать. Тогда при отсутствии в списке выбора нужной константы ничего не произойдет и оператор выбора просто завершит свою работу.


Оператор выбора Паскаля работает следующим образом. Вначале вычисляется значение выражения <ключ_выбора>, а затем в последовательности <список_выбора> отыскивается константа, равная вычисленному значению. Выполняется оператор, который следует за найденной константой, после чего оператор выбора завершает работу. Если в списке выбора не будет найдена константа, соответствующая вычисленному значению ключа выбора, управление передается операторам, стоящим за словом 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;

end.

1.6. Операторы цикла. Оператор цикла с предусловием. Оператор цикла с постусловием. Оператор цикла с параметром


Цикл — разновидность управляющей конструкции в высокоуровневых языках программирования, предназначенная для организации многократного исполнения набора инструкций. Также циклом может называться любая многократно исполняемая последовательность инструкций, организованная любым способом (например, с помощью условного перехода).


Определения


Последовательность инструкций, предназначенная для многократного исполнения, называется телом цикла. Единичное выполнение тела цикла называется итерацией. Выражение определяющее, будет в очередной раз выполняться итерация, или цикл завершится, называется условием выхода или условием окончания цикла (либо условием продолжения в зависимости от того, как интерпретируется его истинность — как признак необходимости завершения или продолжения цикла). Переменная, хранящая текущий номер итерации, называется счётчиком итераций цикла или просто счётчиком цикла. Цикл не обязательно содержит счётчик, счётчик не обязан быть один — условие выхода из цикла может зависеть от нескольких изменяемых в цикле переменных, а может определяться внешними условиями (например, наступлением определённого времени), в последнем случае счётчик может вообще не понадобиться.


Исполнение любого цикла включает первоначальную инициализацию переменных цикла, проверку условия выхода, исполнение тела цикла и обновление переменной цикла на каждой итерации. Кроме того, большинство языков программирования предоставляют средства для досрочного управления циклом, например, операторы завершения цикла, то есть выхода из цикла независимо от истинности условия выхода (в языке Си — break) и операторы пропуска итерации (в языке Си — continue).


Виды циклов


Безусловные циклы


Иногда в программах используются циклы, выход из которых не предусмотрен логикой программы. Такие циклы называются безусловными, или бесконечными. Специальных синтаксических средств для создания бесконечных циклов, ввиду их нетипичности, языки программирования не предусматривают, поэтому такие циклы создаются с помощью конструкций, предназначенных для создания обычных (или условных) циклов. Для обеспечения бесконечного повторения проверка условия в таком цикле либо отсутствует (если позволяет синтаксис, как, например, в цикле LOOP…END LOOP языка Ада), либо заменяется константным значением (while true do … в Паскале).


Цикл с предусловием


Цикл с предусловием — цикл, который выполняется пока истинно некоторое условие, указанное перед его началом. Это условие проверяется до выполнения тела цикла, поэтому тело может быть не выполнено ни разу (если условие с самого начала ложно). В большинстве процедурных языков программирования реализуется оператором while, отсюда его второе название — while-цикл.


На языке Pascal цикл с предусловием имеет следующий вид:

while <условие> do begin

<тело цикла>

end;


На языке Си:

while(<условие>)

{

<тело цикла>

}


Цикл с постусловием


Цикл с постусловием — цикл, в котором условие проверяется после выполнения тела цикла. Отсюда следует, что тело всегда выполняется хотя бы один раз. В языке Паскаль этот цикл реализует оператор repeat..until; в Си — do…while.

На языке Pascal цикл с постусловием имеет следующий вид::

repeat

<тело цикла>

until <условие>


На языке Си:

do

{

<тело цикла>

}

while(<условие>)


В трактовке условия цикла с постусловием в разных языках есть различия. В Паскале и языках, произошедших от него, условие такого цикла трактуется как условие выхода (цикл завершается, когда условие истинно, в русской терминологии такие циклы называют ещё «цикл до»), а в Си и его потомках — как условие продолжения (цикл завершается, когда условие ложно, такие циклы иногда называют «цикл пока»)…..


Цикл cо счётчиком (с параметром)


Цикл со счётчиком — цикл, в котором некоторая переменная изменяет своё значение от заданного начального значения до конечного значения с некоторым шагом, и для каждого значения этой переменной тело цикла выполняется один раз. В большинстве процедурных языков программирования реализуется оператором for, в котором указывается счётчик (так называемая «переменная цикла»), требуемое количество проходов (или граничное значение счётчика) и, возможно, шаг, с которым изменяется счётчик.


for i := 0 to 9 do begin

... тело цикла

end;


В некоторых языках, например, Си и других, произошедших от него, цикл for, несмотря на синтаксическую форму цикла со счётчиком, в действительности является циклом с предусловием. То есть в Си конструкция цикла:

for (i = 0; i < 10; ++i)

{

... тело цикла

}

фактически представляет собой другую форму записи конструкции:

i = 0;

while (i < 10)

{

... тело цикла

++i;

}

То есть в конструкции for сначала пишется произвольное предложение инициализации цикла, затем — условие продолжения и, наконец, выполняемая после каждого тела цикла некоторая операция (это не обязательно должно быть изменение счётчика; это может быть правка указателя или какая-нибудь совершенно посторонняя операция). Для языков такого вида вышеописанная проблема решается очень просто: переменная-счётчик ведёт себя совершенно предсказуемо и по завершении цикла сохраняет своё последнее значение.


1.7 Процедуры и функции. Параметры, локальные и глобальные переменные. Передача параметров по адресу и по значению.

Процедуры и функции в Паскале

При решении рядa зaдaч необходимо повторять одни и те же действия при рaзличных знaчениях пaрaметров в рaзных чaстях прогрaммы. Для этого используют подпрогрaммы – процедуры и функции. Глaвное рaзличие между ними в том, что функция может быть использовaнa в вырaжении, нaпример:

х: =sin(a);


Процедурa может быть вызвaнa, нaпример:


write(a);

Процедуры и функции в Пaскaле бывaют стaндaртные и нестaндaртные, т.е. определённые пользовaтелем. Стaндaртные функции и процедуры не требуют описaния. В Пaскaле их существует более 200. Некоторые стaндaртные функции были перечислены выше. Примеры стaндaртных процедур: ClrScr – очисткa экрaнa, курсор перемещaется в верхний левый угол. Delay(t) – зaдержкa прогрaммы нa t миллисекунд. GotoXY(x,y) – перемещение курсорa в точку с координaтaми (x,y). Exit – выход из текущего блокa или из прогрaммы. Нестaндaртные процедуры и функции должны быть описaны. Их структурa, в принципе, тaкaя же, кaк и основной прогрaммы. Пример использовaния нестaндaртной процедуры: вычислить



aлгоритм решения: в прогрaмме используется процедурa step, в которой описaно вычисление вырaжения видa xy. Знaчение вырaжения присвaивaется переменной s. При вызове процедуры в блоке оперaторов основной прогрaммы, вместо x,y,s используют-ся другие пaрaметры. Нaпример, при первом вызове процедуры вычисляется вырaжение ab, знaчение которого присвaивaется переменной S1.

Текст прогрaммы нa Пaскaле:

program zet;

var a,b,c,S1,S2,S3,k,r,z:real;

{описaние процедуры}

procedure step(var x,y,s:real);

begin

s:=exp(y*ln(x));

end;

{блок оперaторов}

begin

read (a,b,c,); {ввод дaнных}

step(a,b,S1); {вызов процедуры}

r:=b-c;

step(a,r,S2); {вызов процедуры}

k:= sqr(b)-sqr(c);

step(a,k,S3); {вызов процедуры}

z:=(S1-sqr(S2))/sqrt(S3);

writeln(‘z=’,.z);

end.