KnigaRead.com/
KnigaRead.com » Компьютеры и Интернет » Программирование » Брайан Керниган - Язык программирования Си. Издание 3-е, исправленное

Брайан Керниган - Язык программирования Си. Издание 3-е, исправленное

На нашем сайте KnigaRead.com Вы можете абсолютно бесплатно читать книгу онлайн Брайан Керниган, "Язык программирования Си. Издание 3-е, исправленное" бесплатно, без регистрации.
Перейти на страницу:

Инструкция switch выполняется следующим образом. Вычисляется выражение со всеми побочными эффектами, и результат сравнивается с каждой case-константой. Если одна из case-констант равна значению выражения, управление переходит на инструкцию с соответствующей case-меткой. Если ни с одной из case-констант нет совпадения, управление передается на инструкцию с default-меткой, если такая имеется, в противном случае ни одна из подинструкций switch не выполняется.

В первой версии языка требовалось, чтобы выражение и case-константы в switch были типа int.

A9.5. Циклические инструкции

Циклические инструкции специфицируют циклы.

циклическая-инструкция:

    while (выражение) инструкция

    do инструкция while (выражение)

    for (выражениенеоб ; выражениенеоб ; выражениенеоб ) инструкция

В инструкциях while и do выполнение подинструкций повторяется до тех пор, пока значение выражения не станет нулем. Выражение должно иметь арифметический тип или тип указателя. В while вычисление выражения со всеми побочными эффектами и проверка осуществляются перед каждым выполнением инструкции, a в do - после.

В инструкции for первое выражение вычисляется один раз, тем самым осуществляется инициализация цикла. На тип этого выражения никакие ограничения не накладываются. Второе выражение должно иметь арифметический тип или тип указателя; оно вычисляется перед каждой итерацией. Как только его значение становится равным 0, for прекращает свою работу. Третье выражение вычисляется после каждой итерации и, следовательно, выполняет повторную инициализацию цикла. Никаких ограничений на его тип нет. Побочные эффекты всех трех выражений заканчиваются по завершении их вычислений. Если подинструкция не содержит в себе continue) то

for ( выражение1 ; выражение2 ; выражениеЗ ) инструкция

эквивалентно конструкции

выражение1;

    while (выражение2) {

        инструкция

        выражениеЗ;

}

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

A9.6. Инструкции перехода

Инструкции перехода осуществляют безусловную передачу управления.

инструкция-перехода:

    goto идентификатор ;

    continue ;

    break ;

    return выражениенеоб ;

В goto-инструкции идентификатор должен быть меткой (A9.1), расположенной в текущей функции. Управление передается на помеченную инструкцию.

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

while (...){

    ...

contin: ;

}


do {

    ...

contin: ;

} while (...);


for (...){

    ...

contin: ;

}

инструкция continue, если она не помещена в еще более внутренний цикл, делает то же самое, что и goto contin.

Инструкция break встречается в циклической или в switch-инструкции, и только в них. Она завершает работу самой внутренней циклической или switch- инструкции, содержащей данную инструкцию break, после чего управление переходит к следующей инструкции.

С помощью return функция возвращает управление в программу, откуда была вызвана. Если за return следует выражение, то его значение возвращается вызвавшей эту функцию программе. Значение выражения приводится к типу так, как если бы оно присваивалось переменной, имеющей тот же тип, что и функция.

Ситуация, когда "путь" вычислений приводит в конец функции (т. е. на последнюю закрывающую фигурную скобку), равносильна выполнению return- инструкции без выражения. При этом, а также в случае явного задания return без выражения возвращаемое значение не определено

А10. Внешние объявления

То, что подготовлено в качестве ввода для Си-компилятора, называется единицей трансляции. Она состоит из последовательности внешних объявлений, каждое из которых представляет собой либо объявление, либо определение функции.

единица-трансляции:

    внешнее-объявление

    единица-трансляции внешнее-объявление

внешнее-объявление:

    определение-функции

    объявление

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

A10.1. Определение функции


Определение функции имеет следующий вид:

определение-функции:

    спецификаторы-объявлениянеоб объявитель список-объявленийнеоб

    составная-инструкция

Из спецификаторов класса памяти в спецификаторах-объявлениях возможны только extern и static; различия между последними рассматриваются в A11.2.

Типом возвращаемого функцией значения может быть арифметический тип, структура, объединение, указатель и void, но не "функция" и не "массив". Объявитель в объявлении функции должен явно указывать на то, что описываемый им идентификатор имеет тип "функция", т. е. он должен иметь одну из следующих двух форм (A8.6.3):

собственно-объявитель ( список-типов-параметров )

собственно-объявитель ( список-идентификаторовнеоб )

где собственно-объявитель есть идентификатор или идентификатор, заключенный в скобки. Заметим, что тип "функция" посредством typedef получить нельзя.

Первая форма соответствует определению функции новым способом, для которого характерно объявление параметров в списке-типов-параметров вместе с их типами; за объявителем не должно быть списка-объявлений. Если список-типов-параметров не состоит из одного-единственного слова void, показывающего, что параметров у функции нет, то в каждом объявителе в списке-типов-параметров обязан присутствовать идентификатор. Если список-типов-параметров заканчивается знаками ", ...", то вызов функции может иметь аргументов больше, чем параметров; в таком случае, чтобы обращаться к дополнительным аргументам, следует пользоваться механизмом макроса va_arg из заголовочного файла <stdarg.h>, описанного в приложении B. Функции с переменным числом аргументов должны иметь по крайней мере один именованный параметр.

Вторая форма - определение функции старым способом. Список-идентификаторов содержит имена параметров, а список-объявлений приписывает им типы. В списке- объявлении разрешено объявлять только именованные параметры, инициализация запрещается, и из спецификаторов класса памяти возможен только register.

И в том и другом способе определения функции мыслится, что все параметры как бы объявлены в самом начале составной инструкции, образующей тело функции, и совпадающие с ними имена здесь объявляться не должны (хотя, как и любые идентификаторы, их можно переобъявить в более внутренних блоках). Объявление параметра "массив из типа" можно трактовать как "указатель на тип", аналогично объявлению параметра объявление "функция, возвращающая тип" можно трактовать как "указатель на функцию, возвращающую тип". В момент вызова функции ее аргументы соответствующим образом преобразуются и присваиваются параметрам (см. A7.3.2).

Новый способ определения функций введен ANSI-стандартом. Есть также небольшие изменения в операции повышения типа; в первой версии языка параметры типа float следовало читать как double. Различие между float и double становилось заметным, лишь когда внутри функции генерировался указатель на параметр.

Перейти на страницу:
Прокомментировать
Подтвердите что вы не робот:*