1.4.6 Область видимости и время жизни переменных

По области видимости переменные в Си можно разделить на три группы:

1.Переменная, определенная во всех модулях (файлах) программы. Такая переменная определяется при помощи ключевого слова extern. Эта переменная будет видна во всех точках программы. Такая переменная является глобальной для всей программы.

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

3.Переменная определенная в данной функции. Эта переменная может быть использована только в пределах данной функции. Такую переменную мы будем называть локальной.

По времени жизни все переменные можно разделить на две группы:

1.Переменные живущие в течении работы программы.

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

Глобальные переменные относятся к первому типу по времени жизни. Локальные переменные уничтожаются по выходу из функции. В том случае, когда мы хотим сделать локальную переменную долгоживущей используется слово static. Локальные переменные имеющие такой тип живут начиная с момента первого вызова функции и до конца работы программы. Однако в смысле видимости эти переменные остаются локальными. Запись static int i=0; Означает, что переменная инициализируется нулем при первом входе в функцию, но при последующих входах в функцию ее значение сохраняется в зависимости от тех действий, которые над ней были произведены.

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

И последнее замечание. Динамически выделенная память, где бы вы ее не выделяли живет до тех пор пока вы ее не освободили.

1.5 Основные операторы

Операция присваивания.

Самой общей операцией является присваивание, например, с= a/b. В Си присваивание обозначается знаком равенства=, при этом значение справа от знака равенства присваивается переменной слева. Возможно, применять также последовательные присваивания, например: с = a = b.

Арифметические операторы.

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

1.Бинарные: сложение(+), вычитание(-), умножение(*), деление(/), целочисленное деление(%) (для типа int получение остатка).

2.Унарные: унарный плюс (+), унарный минус (-), адресация (&), косвенная адресация (*), определение размера памяти типа (sizeof).

3.Логические: и (&&), или (!!), не (!=).

4.Отношения:

a)равно (==), не равно(!>);

б) меньше чем (<), больше чем (>), меньше или равно (<=), больше или равно (>=);

5.Приращения (++) и уменьшения (--). Например, i++ обозначает, что i=i+1, а i-- обозначает i=i-1.

6.Побитовые операции - позволяют производить операции над битами.

7.Комбинированные операции. В Турбо-Си существуют сокращения при написании выражений, содержащих многочисленные операции:

a = a + b; сокращается до a += b;

a = a - b; сокращается до a -= b;

a = a * b; сокращается до a *= b;

a = a / b; сокращается до a /= b;

a = a % b; сокращается до a %= b;

8.Адресные операции:

1. Операция определения адреса (&) 2. Операция обращения по адресу (*).

Операция & возвращает адрес данной переменной; если Х является переменной типа int, то &Х является адресом (расположения в памяти) этой переменной. С другой стороны, если msg является указателем на тип char, то *msg является символом, на который указывает msg. Рассмотрим пример:

#include <stdio.h>

main()

{

int X;

char *msg;

X = 6 + 1;

msg = "Привет\n";

printf(" X = %d &X = %p \n",X,&X);

printf("*msg = %c msg = %p \n", *msg, msg);

}

При печати в первой функции печатается два значения: значение X 7 и адрес X (назначаемый компилятором). Во второй функции также печатается два значения: символ, на который указывает msg (П), и значение msg, которое является адресом этого символа (также назначен компилятором).

Старшинство операций в Си соответствует старшинству операций в математике.

Оператор запятая.

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

char X,Y;

(X = Y, Y = getch())

присваивает переменной X значение Y, затем считывает символ, вводимый с клавиатуры, и запоминает его в Y. Результатом всего выражения, в итоге, будет значение введенного с клавиатуры символа.

Операторы управления.

Оператор If... дает возможность в зависимости от условия выполнять ту или иную ветвь программы. Синтаксис оператора следующий:

If условие выражение1 else выражение2;

Условие должно давать результат в виде логического значения истинности или ложности. Выражение1 будет выполняться если условие истинно. Выражение2 будет выполняться если условие ложно.

Существует сокращенный вариант оператора:

If условие выражение1

Пример. Определить, является ли введенное число днем недели, т.е. входит ли число в диапазон от 1 до 7.

#include <stdio.h>

int A;

main()

{

printf("? ");

scanf("%d",&A);

if ((A < 1) || (A > 7))

printf("Error %d\n",A);

else printf("OK %d\n",A);

}

Выражение условия (A<1) || (A>7) будет давать TRUE, если выполняется A<1 или A>7 - в этом случае выполняется ветка printf('Error ',A);, иначе ветка printf('OK ',A);.

Существует другой вариант записи оператора If ... Пример:

#include <stdio.h>

main()

{

int y,t;

printf("? ");

scanf("%d",&t);

y=(t>0)? t*10: t-10; /* if t>0 y=t*10 else y=t-10;*/

printf("OK %d\n",y);

}

В данном варианте вид оператора показан в комментариях.

Оператор switch... case используется в случае, когда необходимо анализировать переменную и в зависимости от ее значения производить те или иные действия. Рассмотрим пример. С клавиатуры вводятся буквы латинского алфавиты. В зависимости от буквы произвести те или иные действия.

#include <stdio.h>

char A;

main()

{

printf("? ");

scanf("%c",&A);

switch (A) {

case 'c': printf(" smoll %c\n",A); break; /* выход из блока */

case 'F':

case 'G': printf(" big %c\n",A);

break;

default: printf("Error %c\n",A);

}

}

В данном примере если введен символ с, то выполняется printf(" smoll %c\n",A);, если вводится заглавные буквы F или G, то выполняется printf(" big %c\n",A);, если не один из рассмотренных символов не вводится, то выполняется printf("Error %c\n",A);.

Для повторения некоторого множества команд несколько раз можно использовать оператор do... while. Рассмотрим пример.

#include <stdio.h>

main()

{

int A;

do {

printf("Zifra? ");

scanf("%d",&A);

printf("Error %d\n",A);

} while (!(A == 9));

printf("OK %d\n",A);

}

С клавиатуры вводится число. Выполняется оператор printf("Error %d\n",A);. Далее идет анализ - равно число 9 или нет, если не равно, снова выполняется тело цикла:

printf("Zifra? ");

scanf("%d",&A);

printf("Error %d\n",A).

Если число равно 9, то выполняется оператор printf("OK %d\n",A); и работа цикла заканчивается.

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

Таким образом, смысл рассматриваемого оператора заключается в следующем: "Выполняй тело цикла до тех пор, пока истинно условие".

Оператор while... в отличие от do... while вначале анализирует условие, а затем выполняет тело цикла.

Пример.

#include <stdio.h>

main()

{

int A;

A = 0;

while (A != 9)

{

printf("Zifra? ");

scanf("%d",&A);

printf("Error %d\n",A);

}

printf("OK %d\n",A);

}

В данном примере инициализирована переменная A:=0;. Это сделано, потому что вначале идет анализ равна она 9 или нет. Если не равна, то выполняется тело цикла. Смысл рассматриваемого оператора заключается в следующем:

«Пока истинно условие выполняй тело цикла».

Оператор for... используется, когда известно сколько раз необходимо выполнить тело цикла, но этот оператор горазда гибче по сравнению с Паскалем. Рассмотрим пример.

#include <stdio.h>

int A;

main()

{

for (A = 1; A <= 5; A++) /* A++ означает A=A-1 */

printf("Zifra %d\n",A);

}

В этом примере A хранит состояние счетчика цикла. Первоначально A:=1. Выполняется оператор printf("Zifra %d\n",A). Далее значение A увеличивается на единицу. Идет анализ A<=5 или нет. Если A больше 5, то цикл заканчивает работу. Если нет, то снова выполняется оператор printf("Zifra %d\n",A).

В следующем примере рассмотрим вариант оператора for..., когда начальное значение переменной больше конечного, а переменная во время работы цикла уменьшается на единицу.

#include <stdio.h>

int A;

main()

{

for (A = 5; A >= 1; A--) /* A-- означает A=A-1 */

printf("Zifra %d\n",A);

}

Существует множество модификаций оператора for..., например:

- пустой оператор - для временной задержки:

for (n=1;n <=10000;n++)

; /* пустой оператор */

- использование различного шага:

for (n=1;n <=230;n=n+10)

- изменение переменных:

for (x=2;n*n <=476;n=5*x++)

Рассмотрим пример, в котором инициализируются две переменные и каждая из которых, изменяется после итерации цикла:

#include <stdio.h>

#define f 30

#define n 19

main()

{

int y,t;

for (y = 1,t=f; y<=16; y++,t+=n) /*t+=n означает t=t+n*/ printf(" %3d %7d\n",y,t);

}

Далее рассмотрим, операторы ветвления (операторы перехода из одной части программы в другую).

Оператор goto позволяет передавать управление на любую строку программы. Для этой цели используется метка. Пример.

#include <iostream.h>

#include <stdio.h>

main()

{

char A;

label_1:/* метка */ printf("? \n");

cin>>A;

if (A != 'y') goto label_1; }

Для прерывания цикла по некоторому условию можно использовать оператор break. Пример.

#include <stdio.h>

#include <iostream.h>

char A;

int I;

main()

{

for (I = 1; I <= 10; I++)

{

printf("? \n");

cin >>A;

i (A == 'y') break;

}

}

Для прерывания итерации цикла и перехода к следующей итерации используется оператор Continue. Пример.

#include <stdio.h>

#include <iostream.h>

char A;

int I;

main()

{

for (I = 1; I <= 10; I++)

{

printf("? \n");

cin >>A;

if (A == 'y') continue;

printf("Работает %c\n",A);

}

}

Для прерывания программы также используются операторы return() и exit().


Информация о работе «Основы C»
Раздел: Информатика, программирование
Количество знаков с пробелами: 200759
Количество таблиц: 5
Количество изображений: 11

Похожие работы

Скачать
20474
0
0

... . Имеет ли право на существование эта биологизаторская интерпретация экологии? Видимо, да. Она широко представлена, и с этим следует считаться. Но она не может служить концептуальной основой комплексного непрерывного экологического образования. В структуре научного знания при таком подходе не остаётся места для географической и социальной экологии, экологии человека, а сама биология превращается ...

Скачать
5443
0
0

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

Скачать
8522
1
2

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

Скачать
11185
0
0

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

0 комментариев


Наверх