![]()
Главная Обратная связь Дисциплины:
Архитектура (936) ![]()
|
Одноместные и двуместные операции
Однооперандные операции. - арифметическое отрицание.Операнд должен быть указан справа от операции. Используется для всех числовых типов данных. Результат операции - число с обратным знаком. Пример: // Переменной а присвоить число со знаком, обратным числу в b а = -b ; // К значению а прибавить значение Ь с обратным знаком с = а + -b ; // Вывести на экран значение х с обратным знаком printf("Число, обратное значению х %d\n", -x); +унарный плюс - получение числа с тем же знаком (не используется). ++ инкремент, или увеличение переменной на единицу. ‑ ‑декремент, или уменьшение переменной на единицу.
Кроме этих обычных операций, Си имеет некоторые специальные одноместные операторы приращения (++) и уменьшения (--). Они позволяют использовать единственную операцию, которая добавляет 1 или вычитает 1 из любого значения. Рассмотрим следующие строки программы: sum = a + b++; sum = a + ++b; Первая означает “сложить а и b, присвоить результат sum и увеличить b на единицу”. Вторая означает “увеличить b на единицу, сложить a и b и присвоить результат sum”. Это очень мощные операции, расширяющие возможности языка. #include <stdio.h> main( ) { int a,b,sum; char *format; format = "a = %d b = %d sum = %d \n"; a = b = 5; sum = a + b ;printf(format,a,b,sum); sum = a++ + b;printf(format,a,b,sum); sum = ++a + b;printf(format,a,b,sum); sum = --a + b;printf(format,a,b,sum); sum = a-- + b;printf(format,a,b,sum); } Си поддерживает обычный набор арифметических операций: · умножение (*), · деление (/), · целочисленное деление (%), т.е. остаток от деления целых чисел. · сложение (+), · вычитание (-). У операции деления есть некоторые особенности. 1. При делении целых чисел получается целый результат. Например, результатом выражения 7/2 будет число 3, а не 3,5. Если хотя бы одно из чисел будет вещественным, то результат будет вещественным. Например, результатом выражения 7 . /2 будет число 3,5. 2. Делить на ноль нельзя. Если программа выполнит эту операцию, она буде выгружена системой за неправильные действия и прекратит свою работу. Это касается и операции получения остатка от деления. Все операции, кроме операции %, можно использовать со всеми рассмотренными типами данных. Операцию получения остатка от деления можно применять только при работе с целыми типами. Результатом выражения 7%4 будет число 3. Если необходимо разделить 7 яблок между 4 людьми поровну без разрезания яблок, то останется 3 яблока, которые на 4 человека не делятся нацело. Эта операция в программировании часто применяется для определения кратности. Например, известно, что номер високосного года кратный четверке - должен разделиться на 4. Поэтому, если в переменной yearсодержится номер года, то для определения, является ли этот год високосным, необходимо применить выражение year% 4и если результат будет равным нулю - то год високосный. Иногда эту операцию используют для ограничения диапазона получаемых чисел, поскольку остаток от деления не может быть больше и даже равен знаменателю. Например, в языке Си имеется функция rand,результатом работы которой является псевдослучай ное число в диапазоне от 0до RAND_MAX.Значение RAND_MAXзависит от реализации функции, но должно быть не меньше 32767. Для того, чтобы ограничить диапазон получаемых чисел, можно получить остаток от деления результата функции randна значение, на единицу больше требуемого верхнего диапазона. Например,_ // получить псевдослучайное число в диапазоне от 0 до 19 х = rand()%20;
Адресные операции Си поддерживает две специальные адресные операции: операцию определения адреса (&) и операцию обращения по адресу (*). Операция &возвращает адрес данной переменной: еслиsum является переменной типа int, то &sum является адресом (расположением в памяти) этой переменной. С другой стороны, если msgявляется указателем на тип char, то *msg является символом, на который указывает msg. Операции сравнения Операции сравнения позволяют сравнивать два значения, причем результат в зависимости от сравнения может быть либо “истина”(значение равно 1) или “ложь” (значение равно 0). Список операций сравнения приведен ниже: - больше, < - меньше, <= - меньше или равно, == - равно, != - не равно. Операции сравнения в основном используются в условных операторах, которые рассматриваются ниже. Другие логические операции. Однооперандные операции. ! логическое отрицание. Применяется для получения обратного результата от логических выражений. Ниже показаны результаты работы этой операции: !1 равно 0. !0 равно 1. Если логическим операциям указать значение, отличное от нуля, то оно будет восприниматься как истина. Пример: !5 равно 0 Примеры отрицания простых логических выражений: не интересует значение переменной х, если оно больше 10 ! (а > 10) интересует любое значение переменной х, кроме 0 ! (х = 0) интересует не високосный год !(уеаг%4 = 0)________________________________________________ Круглые скобки в выражениях нужны, поскольку операция логического отрицания имеет более высокий приоритет, нежели те операции, которые применены в выражениях. Логические операции Логические операции работают с логическими выражениями и позволяют составлять логические выражения. Имеются три такие операции: операция “И” - &&При объединении этой операцией двух логических выражений в одно, составное выражение будет истинно только тогда, когда оба простых выражения будут истинны. Например, выражение: а > 10 && а < 20 будет истинно, если в переменной а будет находиться число в диапазоне от 11 до 19.
операция “ИЛИ” - ||При объединении этой операцией двух логических выражений в одно, составное выражение будет истинно тогда, когда хотя бы одно простое выражение будет истинным. Например, выражение: а < 10 || а > 20 будет истинно, если в переменной а будет находиться число меньше 10 или больше 20. операция “НЕ” -! Эти операции всегда дают в результате значения либо 0 (ложь), либо 1 (истина). Побитовые операции Побитовые операции применимы только для целых типов данных и часто используются для анализа и управления значениями двоичных разрядов чисел. Результат работы этих операций есть смысл смотреть только в двоичной системе счисления. Однооперандные операции. ~ двоичное отрицание- инвертирует разряды двоичного числа. Пример: ~ 11010101 число 001010102 результат Применяется для получения обратных чисел. Двухоперандные операции. Все двухоперандные побитовые операции, за исключением сдвиговых, выполняются над парами двоичных разрядов двух чисел по таблице. & побитовое И. Эта операция выполняется по следующей таблице:
Пример выполнения: 011010102 число1 & 010111012 число2 010010002 результат Часто эту операцию в программировании используют для тестирования состояния двоичного разряда числа - определения его содержимого. Для этого выполняют операцию И над числом и вторым числом, которое должно содержать 1 в интересующем разряде и 0 в остальных. Если в результате операции получится 0, то и в интересующем разряде находится 0, в противном случае 1. Пример тестирования 4-го разряда: Если число находится в переменной х, то выражение для выполнения тестирования четвертого разряда в этой переменной, на языке Си будет выглядеть следующим образом: (х & 16) = 0 Второе широкое применение этой операции для сброса двоичного разряда числа - записи в интересующий разряд 0. Для этого необходимо выполнить операцию И над числом и вторым числом, которое должно содержать в интересующем разряде 0 в остальных 1. Оно обратно числу, используемому для тестирования, и может быть получено операцией НЕ. Пример сброса 4-го разряда: Если необходимо в числе, находящемся в переменной х, в четвертый двоичный разряд записать 0, то это может быть сделано следующим выражением: х= х& OxEF; // или х= х& -16; Число 111011112 в шестнадцатеричной системе счисления имеет представление EF. Вместо константы OxEF, можно было применить константу 239 или 0357, поскольку это разные представления одного и того же числа. | побитовое ИЛИ. Эта операция выполняется по следующей таблице:
Пример выполнения: 011010002 число1 1 0101П012 число2 011111012 результат Широко эта операция применяется для установки двоичного разряда числа в 1. Для этого выполняют операцию ИЛИ над числом и вторым числом, которое должно содержать 1 в интересующем разряде и 0 в остальных. Пример установки 4-го разряда в 1: Если необходимо в числе, находящемся в переменной х, в четвертый двоичный разряд записать 1, то это может быть сделано следующим выражением: х = х | 16 ;_ ^ побитовое ИСКЛЮЧАЮЩЕЕ ИЛИ. Таблица для этой операции следующая:
Пример выполнения: << сдвиг двоичных разрядов числа влево. >> сдвиг двоичных разрядов числа вправо. Второй операнд у этих операции должен указывать, на сколько позиций сдвигать разряды. Те разряды, которые выходят за рамки числа, теряются, а вновь прибывающие приходят с нулями при сдвиге влево. При сдвиге вправо знакового числа, если оно отрицательное, происходит заполнение числа единицами, для сохранения знака. Пример: Сдвиговые операции можно использовать для формирования чисел, необходимых для тестирования и установки разрядов числа. Например, для того, что бы получить число для тестирования разряда с номером п, можно воспользоваться выражением 1 « n. Операция сдвига числа влево на nразрядов равносильна умножению этого числа на 2n, а сдвиг числа вправо на nразрядов равносилен делению числа на 2n. Поскольку сдвиговые операции выполняются в компьютере быстрее, нежели арифметические операции, то иногда их используют для реализации умножения или деления числа на 2n. Прочие операции Однооперандные операции & получение адреса переменной.Используется для переменных любых типов. Результатом работы этой операции будет адрес первого байта, с которого начинается переменная в оперативной памяти. Пример:__________________________________________________________________ scanf("%d", &a) ///функции sacnf передается адрес переменной sizeof операция определения размера. Записывается по следующей форме:________ sizeof(тип_данных) или sizeof(выражение) Результатом работы этой операции будет целое число, которое будет отражать размер операнда в байтах. Результатом выражения sizeof (double)будет число 8, а выражение sizeof (a + b)даст число 4, если переменные аи b типа long. Удобно использовать эту операцию с типом intв случае написания переносимого под разные платформы текста программы, т.к. размер у этого типа в языке Си плавает и зависит от разрядности процессора. (тип__данных)операция приведения типа. Позволяет преобразовать значение одного типа данных в другой. Например, для того, чтобы получить остаток от деления целых частей переменных аи bтипа doubleможно воспользоваться выражением (int)a% (int)b.Без приведения к типу intкомпилятор будет выдавать ошибку, т.к. операцию получения остатка от деления целых чисел нельзя применять к переменным типа double. Двухоперандные операции , операция последовательного вычисления. Задается по следующей форме: выражение1 , выражение2 Результатом операции будет результат от вычисления выражения2.Удобна в тех случаях, когда по синтаксису языка Си требуется указать одно выражение, а для организации работы программы требуется два. Пример:_ х = (а > b) ? а+= 10, а- b ; b += 10 , b - а; переменной хприсвоить абсолютное значение разности двух чисел аи b, при этом большее число необходимо увеличить на 10 перед вычислением разности. Арифметические преобразования данных В выражениях языка Си могут встречаться разные типы данных, при этом компилятор осуществляет автоматически преобразование операндов к одному типу, а затем реализует операцию. Типом результата будет тип, к которому осуществлялось преобразование операндов. Арифметические преобразования осуществляются следующим образом: 1. Все операнды типов char или short преобразуются к int, все операнды типов unsigned char или unsigned short преобразуются к unsigned int, все операнды типа float преобразуются к типу double. 2. Любую пару разнотипных операндов компилятор рассматривает в следующем порядке: если один операнд типа long double, то второй преобразуется к типу long double, если один операнд типа double, то второй преобразуется к типу double, если один операнд типа unsigned long, то второй преобразуется к типу unsigned long, если один операнд типа long, то второй преобразуется к типу long. 3. В операторе присваивания операнд (результат) в правой части преобразуется к типу переменной в левой части, при этом тип может, как повышаться, так и понижаться. Благодаря этим преобразованиям в программах удается получать правильные результаты и меньше заботиться о диапазонах типов.
Ввод В Си имеется несколько функций ввода; некоторые производят ввод из файла или входного потока, другие с клавиатуры. Здесь рассматривается только ввод с клавиатуры, а операции ввода/вывода из файла приведены ниже. Функция scanf Для интерактивного ввода можно использовать в большинстве случаев функцию scanf. Эта функция по смыслу эквивалентна printf; ее формат выглядит так: scanf( <строка формата>,<адрес>,<адрес>,...) В функции scanf используются многие из тех спецификаций формата %<буква>, что и у функции printf:%d - для целых, %f - для чисел с плавающей точкой и т.д. Однако scanf имеет одно важное отличие: объекты, следующие за строкой формата, должны быть адресами, а не значениями. Например, в программе содержится следующий вызов: scanf(“%d %d”, &a, &b); Этот вызов сообщает программе, что она должна ожидать ввода двух десятичных (целых) чисел, разделенных пробелом; первое будет присвоено а, а второе - b. Здесь используется операция адреса (&) для передачи адресов а и b функции scanf. Если есть необходимость ввести строку символов, то это делается, например, следующим образом: main() { char name[30]; printf(“Как вас зовут: “); scanf(“%s, name); printf(“Привет, %s\n, name); } Поскольку name является массивом символов, значение name -это адрес самого массива. По этой причине перед именем name не используется адресный оператор &, просто пишется имя name. 8.2.2. Функции gets и getch Функция gets читает все, что набирается на клавиатуре, до тех пор пока не нажата клавиша “Enter”. Она в конец строки помещает нулевой символ (\0). Однако эта функция порождает другую проблему: снова запустите эту программу, однако введите вашу имя и фамилию. Что получилось? Это случилось потому, что введенный после имени пробел сигнализирует о конце вводимой строки. Два варианта решения этой проблемы. Первая состоит в том, чтобы зарезервировать 2 массива - на имя и на фамилию. Тогда в программе модифицируется строка ввода: scanf("%s %s",first,last); Модифицировать программу для ввода и печати на экране имени и фамилии. Второй способ состоит в использовании другой функции ввода gets. Введите следующую программу: main () { char name[60]; printf("Как вас зовут: "); gets(name); printf("Привет, %s\n, name); } Функция gets читает все, что набирается на клавиатуре, до тех пор пока не нажата клавиша "Enter". Она в конец строки помещает нулевой символ (\0). Ввести теперь в этой программе имя и фамилию и посмотреть, как она их выводит. Наконец, есть еще функция getch. Она читает единственныйсимвол с клавиатуры, не выдавая его на экран ( в отличие от scanf и gets). Заметим, что у нее нет параметра, она является функцией типа char, ее значение может быть непосредственно присвоено переменной ch.
![]() |