Студопедия

КАТЕГОРИИ:

АвтоАвтоматизацияАрхитектураАстрономияАудитБиологияБухгалтерияВоенное делоГенетикаГеографияГеологияГосударствоДомЖурналистика и СМИИзобретательствоИностранные языкиИнформатикаИскусствоИсторияКомпьютерыКулинарияКультураЛексикологияЛитератураЛогикаМаркетингМатематикаМашиностроениеМедицинаМенеджментМеталлы и СваркаМеханикаМузыкаНаселениеОбразованиеОхрана безопасности жизниОхрана ТрудаПедагогикаПолитикаПравоПриборостроениеПрограммированиеПроизводствоПромышленностьПсихологияРадиоРегилияСвязьСоциологияСпортСтандартизацияСтроительствоТехнологииТорговляТуризмФизикаФизиологияФилософияФинансыХимияХозяйствоЦеннообразованиеЧерчениеЭкологияЭконометрикаЭкономикаЭлектроникаЮриспунденкция

Бинарные арифметические операции




Занятие 3

Выражения. Переменные. Операции.

Переменные

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

Пример описания целой переменной с именем а и вещественной переменной х:

int a; float x;

Общий вид оператора описания переменных:

[класс памяти]  [const] тип имя [инициализатор];

 

Рассмотрим правила задания составных частей этого оператора.

Необязательный класс памяти может принимать одно из значений auto, extern, static, register. О них расскажу позже.

Модификатор const показывает, что значение переменной изменять нельзя. Такую переменную называют именованной константой, или просто константой.

При описании можно присвоить переменной начальное значение, это называется инициализацией. Инициализатор можно записывать в двух формах - со знаком равенства

= значение

или в круглых скобках

(значение)

Константа должна быть инициализирована при объявлении. В одном операторе можно описать несколько переменных одного типа, разделяя их запятыми.

Примеры.

short int a=1;                       //целая переменная а

const char C = ‘C’;              //символьная константа С

char s, sf = ‘f’;            //инициализация относится только к sf

char t (54);

float c = 0.22, x(3), sum;

 

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

Область действия идентификатора – это часть программы, в которой его можно использовать для доступа к связанной с ним области памяти. В зависимости от области действия переменная может быть локальной или глобальной.

Если переменная определена внутри блока (внутри {}), она называется локальной, область ее действия – от точки описания до конца блока, включая все вложенные блоки. Если переменная определена вне любого блока, она называется глобальной и областью ее действия считается файл, в котором она определена, от точки описания до его конца.

Класс памяти определяет время жизни и область видимости программного обеспечения (в частности, переменной). Если класс памяти не указан явным образом, он определяется компилятором исходя из контекста объявления.

Время жизни может быть постоянным (в течение выполнения программы) и временным (в течение выполнения блока).

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

Для задания класса памяти используются следующие спецификаторы:

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

extern – означает, что переменная определяется в другом месте программы (в другом файле или дальше по тексту). Используется для создания переменных, доступных во всех модулях программы, в которых они объявлены.

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

register – аналогично auto, но память выделяется по возможности в регистрах процессора. Если такой возможности у компилятора нет, переменные обрабатываются как auto.

int a;                 //1 глобальная переменная а

int main()

{

int b;                 // 2 локальная переменная и

extern int x;     // 3 переменная х определена в другом месте

static int c;        // 4 локальная статическая переменная с

a=1;                  // 5 присваивание глобальной переменной

int a;                 // 6 локальная переменная а

a=2;                  // 7 присваивание локальной переменной

:: a=3;               // 8 присваивание глобальной переменной

return 0;

}

int x=4;             // 9 определение и инициализация х

 

В этом примере глобальная переменная а определена вне всех блоков. Память под нее выделяется в сегменте данных в начале работы программы, областью действия является вся программа. Область видимости – вся программа, кроме строк 6-8, т.к. в первой из них определяется локальная переменная с тем же именем, область действия которой начинается с точки ее описания и заканчивается при выходе из блока. Переменные b и с – локальные, область видимости – блок, но время жизни различно: память по b выделяется в стеке при входе в блок и освобождается при выходе из него, а переменная с располагается в сегменте данных и существует все время, пока работает программа.

Если при определении начальное значение переменных явным образом не задается, компилятор присваивает глобальным и статическим переменным нулевое значение соответствующего типа. Автоматические переменные не инициализируются.

Имя переменной должно быть уникальным в своей области действия (например, в одном и том же блоке не может быть двух переменных с одинаковыми именами). Имя должно отражать смысл хранимой величины, быть легко распознаваемым и желательно не содержать символов, которые можно перепутать друг с другом (l (строчная L), 1, I (большая i)). Для разделения частей имени можно использовать _.

Описание переменной может выполняться в форме объявления или определения. Объявление информирует компилятор о типе переменной и классе памяти, а определение содержит, кроме того, указание компилятору выделить память в соответствии с типом переменной. В С++ большинство объявлений являются одновременно и определениями. В примере только описание 3 является объявлением, но не определением.

Переменная может быть объявлена многократно, но определена только в одном месте программы, т.к. объявление просто описывает свойство переменной, а определение связывает ее с конкретной областью памяти.

 



Операции

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

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

Знак операции – это символ или группа символов, сообщающих компилятору о необходимости выполнений арифметических, логических или других действий.

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

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

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

- Унарные (с одним операндом);

- Бинарные (с двумя операндами);

- Тернарные (с тремя операндами.

В таблице 1 приведен список основных операций, определенных в С++ в соответствие с их приоритетами (по убыванию приоритетов).

Таблица 1. Основные операции языка С++

Операция краткое описание

Унарные операции (одинаковый приоритет)

++ увеличение на 1
-- уменьшение на 1
sizeof размер
~ поразрядное отрицание
! логическое отрицание
- арифметическое отрицание (унарный минус)
+ унарный плюс
& взятие адреса
* разадресация
new выделение памяти
delete освобождение памяти
(type) преобразование типа

Бинарные и тернарные операции

* / % умножение деление остаток от деления
+ - сложение вычитание
<< >> сдвиг влево сдвиг вправо
< <= > >= меньше меньше или равно больше больше или равно
== != равно не равно
& поразрядная конъюнкция (И)
^ поразрядное исключающее ИЛИ
| поразрядная дизъюнкция (ИЛИ)
&& логическое И
|| логическое ИЛИ
?: условная операция (тернарная)
= *= /= %= += -= <<= >>= &= |= ^= присваивание умножение с присваиванием деление с присваиванием остаток от деления с присваиванием сложение с присваиванием вычитание с присваиванием сдвиг влево с присваиванием сдвиг вправо с присваиванием поразрядное И с присваиванием поразрядное ИЛИ с присваиванием поразрядное исключающее ИЛИ с присваиванием
, последовательное вычисление

 

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

Операция присваивания обозначается символом "=", ее простейший вид L = r.

Операция присваивания выполняется справа налево, т.е. сначала вычисляется значение выражение r, а затем это значение присваивается операнду L, причем левый операнд должен быть адресным выражением, т.е. объектом, размещенным в памяти компьютера.

Примером адресного выражение является имя переменной. Примерами неадресного выражения могут быть выражения, например, a + b, а также константы, которые могут стоять только справа. Отметим, что в С/С++ возможна такая запись:

A = b = c = в = у+2.

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

Примеры потери результата:

int i;

char ch;

i=3.14;

ch = 777;

здесь i получает значение 3, так как теряется дробная часть числа 3,14, а значение 777 слишком велико, и потому не может быть размещено в char-переменной. Отметим, что максимальное число, которое можно записать в один байт – это 377.

Существует так называемая комбинированная операция присваивания вида: a оп= b, здесь "оп" является знаком одной из бинарных операций:

+ - * / % >> << & | ^ && ||

Выражение a оп= b эквивалентно выражению a = а оп b.

Примеры.

а += 2 означает а = а+2;

s / = a означает s = s / a.

выражение а += 2 выполняется быстрее, чем а = а + 2 и потому компактная запись предпочтительнее. Дело в том, что прежде чем приступить к вычислению, заданному операцией "+", необходимо вычислить адрес операнда а. В первом выражении адрес вычисляется один раз, а во втором – дважды. Подобная экономия на вычислении адресов операндов является характерной чертой языка С.

Следующий пример демонстрирует еще один прием компактной записи вычислений:

Выражение (а=b)+=с эквивалентно двум операторам:

a=b; a = a + c.

 

Бинарные арифметические операции

Бинарными арифметическими операциями являются:

+ сложение;

- Вычитание;

* умножение;

/ деление;

% деление по модулю (остаток от деления).

 Рассмотрим выражения, в которых используются разнотипные данные, именно в этом случае проявляются особенности вычисление при помощи компьютера. Как известно, данные (как операнды, так и результат) должны быть размещены в памяти компьютера, причем объем занимаемой памяти зависит от типа данных. Если при вычислении тип операндов отличается от типа результата, то это следует учитывать при распределении памяти (объявлении переменных).

Пример.

Результат выражения i*f преобразуется к типу double (к большему из двух типов), затем результат присваивается переменной g.

int i = 5;

double g, f = 0.2;

g = f*i;

 

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

int k=10, m=3, x;

x = k/m;            // x=3;

int L=10;

double p=3, z;

z = L / p;           // z =3,33333..

 

Пример. Операция а % b применяется только к целым операндам и дает остаток от деления а на b.

x = 10 % 3;       // x=1

y = 2 % 3;         // y = 2

z = 12 % 2;       // z= 0

 

2.3 Операции увеличения (++) и уменьшения (--)

Во многих алгоритмах в цикле требуется наращивание (или уменьшение) значения переменных на единицу, такие переменные называют счетчиками. Назначение счетчиков различно и используются они настолько часто, что во многих языках программирования существует специальный оператор увеличения значения переменной на единицу, называемый инкрементом. Оператор var ++ выполняет то же действие, что и оператор var = var +1.

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

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

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

 Пример.

#include <stdio.h>

int main()

{

      int x=3, y=3;

printf("Значение префиксного выражения: %d\n", ++x);

printf("Значение постфиксного выражения: %d\n", y++);

printf("Значение x после приращения: %d\n", x);

printf("Значение у после приращения: %d\n", у);

return 0;

}

Результат работы программы:

Значение префиксного выражения: 4

Значение постфиксного выражения: 3

Значение x после приращения: 4

Значение у после приращения: 4

Пример.

int t=1, s=2, z, f;

z = (t++)*5;      //z=5, t = 2

f = (++s) / 3;     // s=3, f=1.

 

Вначале вычисляется t*5, а затем t++. Аналогично вначале вычисляется s++, а затем s/3.

Если операции увеличения и уменьшения используются как самостоятельные операторы, префиксная и постфиксная формы записи становятся эквивалентными.

 










Последнее изменение этой страницы: 2018-05-10; просмотров: 165.

stydopedya.ru не претендует на авторское право материалов, которые вылажены, но предоставляет бесплатный доступ к ним. В случае нарушения авторского права или персональных данных напишите сюда...