Программирование >>  Инициализация объектов класса, структура 

1 ... 54 55 56 [ 57 ] 58 59 60 ... 395


побитовое ИЛИ

expr expr

логическое И

expr ss expr

логическое ИЛИ

expr expr

условный оператор

expr ? expr * expr

присваивание

l-значение = expr

- *- /- о-

=, *=, /=, %=,

+=, -=, <<=, >>=,

составное присваивание

l-значение += expr и т.д.

throw

возбуждение исключения

throw expr

запятая

expr, expr

4.14. Преобразования типов

int ival = 0;

/ / обгчно компилируется с предупреждением

Представим себе следующий оператор присваивания:

ival = 3.541 + 3;

В результате ival получит значение 6. Вот что происходит: мы складываем литералы разн1х типов - 3.541 типа double и 3 типа int. C++ не может непосредственно сложить подобные операнды, сначала ему нужно привести их к одному типу. Для этого существуют правила преобразования арифметических типов. Общий принцип таков: перейти от операнда меньшего типа к большему, чтобы не потерять точность вычислений.

В нашем случае целое значение 3 трансформируется в тип double, и только после этого производится сложение. Такое преобразование выполняется независимо от желания программиста, поэтому оно получило название неявного преобразования типов.

Результат сложения двух чисел типа double тоже имеет тип double. Значение равно 6.541. Теперь его нужно присвоить переменной ival. Типы переменной и результата 6.541 не совпадают, следовательно, тип этого значения приводится к типу переменной слева от знака равенства. В нашем случае это int. Преобразование double в int производится автоматически, отбрасыванием дробной части (а не округлением). Таким образом, 6.541 превращается в 6, и этот результат присваивается переменной ival. Поскольку при таком преобразовании может быть потеряна точность, большинство компиляторов выдают предупреждение.

Так как компилятор не округляет числа при преобразовании double в int, при

double dva1 = 8.6; int iva1 = 5;

необходимости мы должны позаботиться об этом сами. Например:



инструкция компилятору привести double к int

При желании м1 можем произвести явное преобразование типов:

ival = static cast< int >( 3.541 ) + 3;

В этом примере мы явно даем указание компилятору привести величину 3.541 к типу int, а не следовать правилам по умолчанию.

В этом разделе мы детально обсудим вопросы и неявного (как в нервом примере), и явного преобразования типов (как во втором).

4.14.1. Неявное преобразование типов

Язык определяет набор стандартных преобразований между объектами встроенного тина, неявно выполняющихся компилятором в следующих случаях:

арифметическое выражение с операндами разных типов: все операнда: приводятся к наибольшему типу из встретившихся. Это называется

int ival = 3;

double dva1 = 3.14159;

ival преобразуется в double: 3.0

арифметическим преобразованием. Например:

ival + dva1;

присваивание значения выражения одного типа объекту другого типа. В этом случае результирующим является тип объекта, которому значение присваивается. Так, в нервом примере литерал 0 тина int присваивается указателю тина int*,

0 преобразуется в нулевой указатель типа int* int *pi = 0;

dva1 преобразуется в int: 3

значением которого будет 0. Во втором примере double преобразуется в int.

ivat = dva1;

передача функции аргумента, тип которого отличается от типа соответствующего формального параметра. Тип фактического аргумента

extern double sqrt( double ); 2 преобразуется в double: 2.0 приводится к типу параметра:

cout << Квадратн корень из 2: << sqrt( 2 ) << endt;

ival += dva1 + 0.5; преобразование с округлением



double difference( int ivati, int iva12 ) {

результат преобразуется в double return ivati - iva12;

возвращаемого значения приводится к объявленному. Например:

4.14.2. Арифметические преобразования типов

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

типы всегда приводятся к тому из типов, который способен обеспечить наибольший диапазон значений при наибольшей точности. Это помогает уменьшить потери точности при преобразовании;

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

М1 рассмотрим иерархию правил преобразований, начиная с наибольшего типа long double.

Если один из операндов имеет тип long double, второй приводится к этому же типу в любом случае. Например, в следующем выражении символьная константа a трансформируется в long double (значение 97 для представления ASCII) и затем прибавляется к литералу того же типа: 3.14159L + a.

Если в выражении нет операндов long double, но есть операнд double, все

int iva1; float fval; double dval;

/ / fva1 и iva1 преобразится к double перед сложением

преобразуется к этому типу. Например:

dval + fva1 + ival;

В том случае, если нет операндов типа double и long double, но есть операнд float,

char cvat; int iva1;

float fva1;

iva1 и cval преобразится к float перед сложением

тип остальных операндов меняется на float:

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



1 ... 54 55 56 [ 57 ] 58 59 60 ... 395

© 2006 - 2024 pmbk.ru. Генерация страницы: 0
При копировании материалов приветствуются ссылки.
Яндекс.Метрика