Язык программирования Си для персонального компьютера
Шрифт:
/********************
Комментарий может занимать
несколько строк.
********************/
Так как комментарии не могут содержать вложенных комментариев, то следующий пример будет ошибочным:
/* Недопустимы /* вложенные */ комментарии */
Компилятор языка Си распознает первую комбинацию символов */ после слова "вложенные" как конец комментария. Затем компилятор языка Си попытается обработать оставшийся текст и выявить в нем лексемы языка Си, что приведет к ошибке.
Во избежание случайного возникновения ситуации вложенности комментариев рекомендуется ограничивать участок
В СП ТС существует опция компиляции, допускающая вложенные комментарии.
СТРУКТУРА ПРОГРАММЫ
Исходная программа
Исходная программа представляет собой совокупность следующих элементов: директив препроцессора, указаний компилятору, объявлений и определений. Директивы препроцессора специфицируют действия препроцессора по преобразованию текста программы перед компиляцией. Указания компилятору — это специальные инструкции, которым компилятор языка Си следует во время компиляции.
Объявление переменной задает имя и атрибуты переменной. Определение переменной, помимо задания ее имени и атрибутов, приводит к выделению для нее памяти. Кроме того, определение задает начальное значение переменной (явно или неявно).
Объявление функции задает ее имя, тип возвращаемого значения и может задавать атрибуты ее формальных параметров.
Определение функции специфицирует тело функции, которое представляет собой составной оператор (блок), содержащий объявления и операторы. Определение функции также задает имя функции, тип возвращаемого значения и атрибуты ее формальных параметров.
Объявление типа позволяет программисту создать собственный тип данных. Оно состоит в присвоении имени некоторому базовому или составному типу языка Си. Для типа понятия объявления и определения совпадают.
Исходная программа может содержать произвольное число директив, указаний компилятору, объявлений и определений. Их синтаксис описан в последующих разделах. Порядок появления этих элементов в программе весьма существен; в частности, он влияет на возможность использования переменных, функций и типов в различных частях программы (см. раздел 2.4 "Время жизни и область действия").
Для того чтобы программа на языке Си могла быть скомпилирована и выполнена, она должна содержать по крайней мере одно определение — определение функции. Эта функция определяет действия, выполняемые программой. Если же программа содержит несколько функций, то среди них выделяется одна главная функция, которая должна иметь имя main. С нее начинается выполнение программы; она определяет действия, выполняемые программой, и вызывает другие функции. Порядок следования определений функций в исходной программе несуществен.
Если программа содержит только одну функцию, то она и является главной (и должна иметь имя main). В следующем примере приведена простая программа на языке Си:
int х = 1; /* определения переменных. */
inl у = 2;
extern int printf(char *, ..,); /* объявление функции */
main /* определение главной функции */
{
int z; /* объявления
int w;
z = у + х; /* выполняемые операторы */
w = y – x;
printf("z = %d\nw = %d\n", z, w);
}
Эта исходная программа определяет функцию с именем main и объявляет функцию printf. Переменные х и у определяются на внешнем уровне, а переменные z и w объявляются внутри функции.
Исходные файлы
Текст программы на языке Си может быть разделен на несколько исходных файлов. Исходный файл представляет собой текстовый файл, который содержит либо всю программу, либо ее часть. При компиляции исходной программы каждый из составляющих ее исходных файлов должен быть скомпилирован отдельно, а затем связан с другими файлами компоновщиком. Отдельные исходные файлы можно объединять в один исходный файл, компилируемый как единое целое, посредством директивы препроцессора #include.
Исходный файл может содержать любую целостную комбинацию директив, указаний компилятору, объявлений и определений. Под целостностью подразумевается, что такие объекты, как определения функций, структуры данных либо набор связанных между собой директив условной компиляции, должны целиком располагаться в одном файле, т. е. не могут начинаться в одном файле, а продолжаться в другом.
Исходный файл не обязательно должен содержать выполняемые операторы. Иногда удобно размещать определения переменных в одном файле, а в других файлах использовать эти переменные путем их объявления. В этом случае определения переменных становятся легко доступными для поиска и модификации. Из тех же соображений именованные константы и макроопределения обычно собирают в отдельные файлы и включают их посредством директивы препроцессора #include в те исходные файлы, в которых они требуются.
Указания компилятору обычно действуют только для отдельных участков исходного файла. Специфические действия компилятора, задаваемые указаниями, определяются конкретной реализацией компилятора языка Си.
В нижеследующем примере исходная программа состоит из двух исходных файлов. Функции main и max представлены в отдельных файлах. Функция main использует функцию max в процессе своего выполнения.
/* исходный файл 1 — функция main */
#define ONE 1
#define TWO 2
#define THREE 3
extern int max (int, int); /* объявление функции */
main /* определение функции */
{
int w = ONE, x = TWO, у = THREE;
int z = 0;
z = max(x, y);
z = max(z, w);
}
/* исходный файл 2 — функция max */
int max (a, b) /* определение функции */
int a, b;
{
if ( a > b )
return (a);
else
return (b);
}
В первом исходном файле функция max объявлена, но не определена. Такое объявление функции называется предварительным; оно позволяет компилятору контролировать обращение к функции до того, как она определена. Определение функции main содержит вызовы функции max.