Введение
В этом практическом занятии вы научитесь использовать операторы в C++. Вы узнаете, как использовать арифметические операторы, операторы сравнения, логические операторы и битовые операторы.
Предварительный просмотр содержания
Для базовых числовых и логических данных мы используем операторы для работы с ними. Как и в других языках, C++ обеспечивает полную поддержку операторов. Начните изучать их.
- Арифметические операции
- Операции с смешанными типами
- Комплексные операторы присваивания
- Преобразование типов
- Операторы сравнения и логические операторы
Арифметические операции
C++ поддерживает следующие арифметические операторы для чисел:
| Оператор | Описание | Использование | Примеры |
|---|---|---|---|
| * | Умножение | expr1 * expr2 | 2 3 → 6; 3.3 1.0 → 3.3 |
| / | Деление | expr1 / expr2 | 1 / 2 → 0; 1.0 / 2.0 → 0.5 |
| % | Остаток (модуль) | expr1 % expr2 | 5 % 2 → 1; -5 % 2 → -1 |
| + | Сложение | expr1 + expr2 | 1 + 2 → 3; 1.1 + 2.2 → 3.3 |
| - | Вычитание | expr1 - expr2 | 1 - 2 → -1; 1.1 - 2.2 → -1.1 |
Все вышеперечисленные операторы - это бинарные операторы, они принимают два операнда. Умножение, деление и остаток имеют преимущество перед сложением и вычитанием.
Важно заметить, что int/int дает int, при этом результат отбрасывается, 1/2 → 0 (а не 0.5).
Операции с различными типами
Если оба операнда арифметической операции принадлежат к одному и тому же типу, операция выполняется в этом типе, и результат принадлежит этому типу. Однако, если два операнда принадлежат к разным типам, компилятор преобразует значение меньшего типа в больший тип (известный как неявное преобразование типа). Затем операция выполняется в большем типе.
| Тип | Пример | Операция |
|---|---|---|
| int | 2 + 3 | int 2 + int 3 → int 5 |
| double | 2.2 + 3.3 | double 2.2 + double 3.3 → double 5.5 |
| смешанный | 2 + 3.3 | int 2 + double 3.3 → double 2.0 + double 3.3 → double 5.3 |
| int | 1 / 2 | int 1 / int 2 → int 0 |
| double | 1.0 / 2.0 | double 1.0 / double 2.0 → double 0.5 |
| смешанный | 1 / 2.0 | int 1 / double 2.0 → double 1.0 + double 2.0 → double 0.5 |
Например
/* Testing mix-type arithmetic operations */
#include <iostream>
#include <iomanip> // needed for formatting floating-point numbers
using namespace std;
int main() {
int i1 = 2, i2 = 4;
double d1 = 2.5, d2 = 5.0;
// floating-points in fixed format with 1 decimal place
cout<<fixed<<setprecision(1);
cout << i1 << " + " << i2 << " = " << i1+i2 << endl; // 6
cout << d1 << " + " << d2 << " = " << d1+d2 << endl; // 7.5
cout << i1 << " + " << d2 << " = " << i1+d2 << endl; // 7.0 <==
cout << i1 << " - " << i2 << " = " << i1-i2 << endl; // -2
cout << d1 << " - " << d2 << " = " << d1-d2 << endl; // -2.5
cout << i1 << " - " << d2 << " = " << i1-d2 << endl; // -3.0 <==
cout << i1 << " * " << i2 << " = " << i1*i2 << endl; // 8
cout << d1 << " * " << d2 << " = " << d1*d2 << endl; // 12.5
cout << i1 << " * " << d2 << " = " << i1*d2 << endl; // 10.0 <==
cout << i1 << " / " << i2 << " = " << i1/i2 << endl; // 0 <==
cout << d1 << " / " << d2 << " = " << d1/d2 << endl; // 0.5
cout << i1 << " / " << d2 << " = " << i1/d2 << endl; // 0.4 <==
return 0;
}
Вывод:
2 + 4 = 6
2.5 + 5.0 = 7.5
2 + 5.0 = 7.0
2 - 4 = -2
2.5 - 5.0 = -2.5
2 - 5.0 = -3.0
2 * 4 = 8
2.5 * 5.0 = 12.5
2 * 5.0 = 10.0
2 / 4 = 0
2.5 / 5.0 = 0.5

Переполнение / Переполнение вниз
// Range of int is [-2147483648, 2147483647]
int i1 = 2147483647; // max int
cout << i1 + 1 << endl; // -2147483648 (overflow)
cout << i1 * i1 << endl; // 1
int i2 = -2147483648; // min int
cout << i2 - 1 << endl; // 2147483647 (underflow)
cout << i2 * i2 << endl; // 0
В арифметических операциях результирующее значение переполняется, если оно превышает свою границу. C++ runtime не выдаёт сообщение об ошибке/предупреждении, но даёт неправильный результат. Важно помнить, что проверка переполнения/переполнения вниз - ответственность программиста.
Операторы комбинированного присваивания
C++ также предоставляет так называемые комплексные операторы присваивания, перечисленные ниже:
| Оператор | Использование | Описание | Пример |
|---|---|---|---|
| = | var = expr | Назначить значение слева направо переменной справа | x = 5; |
| += | var += expr | То же, что и var = var + expr | x += 5; то же, что и x = x + 5 |
| -= | var -= expr | То же, что и var = var - expr | x -= 5; то же, что и x = x - 5 |
| *= | var *=*expr* | То же, что и var = var * expr | x = 5; то же, что и x = x 5 |
| /= | var /= expr | То же, что и var = var / expr | x /= 5; то же, что и x = x / 5 |
| %= | var %= expr | То же, что и var = var % expr | x %= 5; то же, что и x = x % 5 |
| ++ | ++x | Предварительный инкремент | y=++x; то же, что и x=x+1;y=x |
| ++ | x++ | Постинкремент | y=x++; то же, что и oldX=x; x=x+1; y=oldX |
| -- | --x | Предварительный декремент | y=--x; то же, что и x=x-1;y=x |
| -- | x-- | Постдекремент | y=x--; то же, что и oldX=x; x=x-1; y=oldX |
x = 5;
cout << x++ << endl; // Сохранить x (5); Увеличить x (=6); Вывести старое x (5).
x = 5;
cout << ++x << endl; // Увеличить x (=6); Вывести x (6).
Неявное преобразование типов против явного приведения типов
Когда вы присваиваете значение базового (встроенного) типа переменной другого базового типа, C++ автоматически преобразует значение в тип приемника, если два типа совместимы. Например:
- Если вы присваиваете значение
intпеременнойdouble, компилятор автоматически преобразует значениеintвdouble(например, из 1 в 1.0) и присваивает его переменнойdouble. - Если вы присваиваете значение
doubleпеременнойint, компилятор автоматически преобразует значениеdoubleв значениеint(например, из 1.2 в 1) и присваивает его переменнойint. Дробная часть будет отброшена и потеряна. Некоторые компиляторы выдают предупреждение/ошибку "возможна потеря точности"; другие нет.
int i;
double d;
i = 3;
d = i; // Присвоить значение int переменной double
cout << "d = " << d << endl; // 3.0
d = 5.5;
i = d; // Присвоить значение double переменной int
cout << "i = " << i << endl; // 5 (отброшено, без предупреждения!)
Вы можете явно выполнять приведение типа с помощью так называемого унарного оператора приведения типа в форме (новый-тип) операнд или новый-тип (операнд). Оператор приведения типа принимает один операнд в определенном типе и возвращает эквивалентное значение в новом типе. Обратите внимание, что это операция, которая дает результирующее значение, аналогично операции сложения, хотя сложение включает два операнда. Например:
cout << (double)5 << endl; // int 5 → double 5.0
cout << (int)5.5 << endl; // double 5.5 → int 5
double aDouble = 5.6;
int anInt = (int)aDouble; // возвращает 5 и присваивает anInt. aDouble не меняется!
// C++ также поддерживает функциональный стиль приведения типа.
cout << double(5) << endl; // 5.0
cout << int(5.5) << endl; // 5
cout << int(aDouble) << endl; // 5
Относительные и логические операторы
Важно отметить, что часто вам нужно сравнивать два значения перед принятием решения о действии, которое необходимо предпринять. C++ предоставляет шесть операторов сравнения (или относительных операторов):
| Оператор | Описание | Использование | Пример (x = 5, y = 8) |
|---|---|---|---|
| == | Равенство | expr1 == expr2 | (x == y) → false |
| != | Неравенство | expr1!= expr2 | (x!= y) → true |
| > | Больше чем | expr1 > expr2 | (x > y) → false |
| >= | Больше или равно | expr1 >= expr2 | (x >= 5) → true |
| < | Меньше чем | expr1 < expr2 | (y < 8) → false |
| <= | Меньше или равно | expr1 >= expr2 | (y <= 8) → true |
| && | Логическое И | expr1 && expr2 | -------- |
| || | Логическое ИЛИ | expr1 || expr2 | -------- |
| ! | Логическое НЕ | !expr | -------- |
| ^ | Логическое ИСКЛЮЧАЮЩЕЕ ИЛИ | expr1 ^ expr2 | -------- |
Таблицы истинности выглядят следующим образом:
| И (&&) | true | false |
|---|---|---|
| true | true | false |
| false | false | false |
| ИЛИ (||) | true | false |
|---|---|---|
| true | true | true |
| false | true | false |
| НЕ (!) | true | false |
|---|---|---|
| false | true |
| ИСКЛЮЧАЮЩЕЕ ИЛИ (^) | true | false |
|---|---|---|
| true | false | true |
| false | true | false |
// Возвращает true, если x находится между 0 и 100 (включительно)
(x >= 0) && (x <= 100)
// неправильно использовать 0 <= x <= 100
// Возвращает true, если x находится вне диапазона от 0 до 100 (включительно)
(x < 0) || (x > 100) //или
!((x >= 0) && (x <= 100))
// Возвращает true, если год является високосным
// Год является високосным, если он делится на 4, но не делится на 100, или если он делится на 400.
((year % 4 == 0) && (year % 100!= 0)) || (year % 400 == 0)
Резюме
Эта часть относительно простая, вы должны связать ее с предыдущим разделом. Не нужно их запоминать, нужно понять их логику.



