Перейти на главную   
  helloworld.ru - документация и книги по программированию  
helloworld.ru - документация и книги по программированию
    главная     хостинг    
Поиск по сайту:  
Смотрите также
Языки программирования
C#
MS Visual C++
Borland C++
C++ Builder
Visual Basic
Quick Basic
Turbo Pascal
Delphi
JavaScript
Java
PHP
Perl
Assembler
AutoLisp
Fortran
Python
1C

Интернет-технологии
HTML
VRML
HTTP
CGI
FTP
Proxy
DNS
протоколы TCP/IP
Apache

Web-дизайн
HTML
Дизайн
VRML
PhotoShop
Cookie
CGI
SSI
CSS
ASP
PHP
Perl

Программирование игр
DirectDraw
DirectSound
Direct3D
OpenGL
3D-графика
Графика под DOS

Алгоритмы
Численные методы
Обработка данных

Сис. программирование
Драйверы

Базы данных
MySQL
SQL

Другое

Хостинг


Друзья
demaker.ru
Реклама

Лучший хостинг. Аренда серверов




helloworld.ru

Преобразование основных типов

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

Однако не всегда в программе удаётся легко согласовать типы операндов и параметров. И здесь проблем, связанных с согласованием типов операндов и параметров транслятор берёт на себя. Фактически это означает введение ещё одной системы правил, которая называется правилами стандартного преобразования типов.

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

1.Присвоение "большему типу" значения "меньшего типа". Безопасное присвоение, гарантирует сохранение значения.

unsigned int UnsignedIntVal;
unsigned char UnsignedCharVal;
UnsignedIntVal = UnsignedCharVal;

2.Присвоение "меньшему типу" значения "большего типа". Потенциально опасное присвоение, грозит потерей информации.

int IntVal;
char CharVal;
CharVal = IntVal;

3.Преобразование значения из "меньшего типа" в "больший тип". Называется расширением типа.

(unsigned int)UnsignedCharVal;

4.Преобразование значения из "большего типа" в "меньший тип". Называется сужением типа. Является опасным преобразованием.

(char)IntVal;

Корректное выполнение действий со значениями различных типов в безопасных случаях и в ряде опасных случаев обеспечивается благодаря реализованной в C++ системе преобразования типов.

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

  • Присваивание значения объекту преобразует это значение к типу объекта.
    unsigned int MyIntU;
    MyIntU = 3.14159;
    Эквивалентно
    MyIntU = (unsigned int)3.14159;
    
  • Передача значения при вызове функции преобразует это значение в тип параметра функции. Он становится известен благодаря прототипу вызываемой функции.
    void ff(int); // Прототип функции.
    :::::
    ff(3.14159);
    

    Эквивалентно ff((int)3.14159);

    При этом на стадии трансляции возможно появление предупреждения о сужении типа.

  • В арифметическом выражении тип результата выражения определяется самым "широким" типом среди всех образующих выражение операндов. Этот тип называют результирующим типом выражения. К этому типу преобразуются все остальные операнды.
    unsigned int MyIntU = 5;
    …(MyIntU + 3.14159)…
    

    Результирующим типом выражения здесь оказывается тип double, представленный в выражении литералом 3.14159. В процессе вычисления выражения значение переменной MyIntU преобразуется в 5.0, к которому прибавляется 3.14159.

  • Преобразование типа при вычислениях арифметических выражений применяется к копиям значений образующих выражение подвыражений. В процессе преобразования типов результаты преобразований подвыражениям не присваиваются.
    unsigned int MyIntU = 5;
    MyIntU = MyIntU + 3.14159;
    

    Здесь имеют место два последовательных преобразования:

    По ходу вычисления выражения значение переменной MyIntU расширяется до double и к расширенной копии значения 5.0 прибавляется 3.14159. После этого результирующее значение 8.14159, в соответствии с первым правилом, сужается до типа unsigned int. В результате чего получается значение 8, которое и присваивается переменной MyIntU.

  • Указатель на любой не являющийся константой тип можно присваивать указателю типа void*. Этот указатель способен адресовать объекты любого типа данных. Он используется всякий раз, когда неизвестен тип объекта.
    int iVal;
    int *p_iVal = 0;
    char *p_chVal = 0;
    void *p_Val;
    const int *pc_iVal = &iVal;
    p_Val = p_iVal;
    p_Val = p_chVal;
    // ПРАВИЛО 5 выполняется...
    p_Val = pc_iVal;
    //Ошибка: pc_iVal - указатель на константу.
    const void *pcVal = pc_iVal;
    /*
    А здесь всё хорошо! Указателю на константу присвоен указатель на константу.
    */
    

    Перед операцией разыменования указатель типа void* нужно явно преобразовать в указатель на конкретный тип, поскольку в этом случае отсутствует информация о типе, подсказывающая транслятору способ интерпретации битовой последовательности, представляемой указателем:

    char *p_chValName = "Marina";
    p_Val = p_chValName;
    p_chVal = (char*)p_Val; /*Явное приведение.*/
    

Механизм неявных преобразований может быть отключён посредством явного указания в тексте программы требуемого преобразования типов.

Так, модификация ранее рассмотренного примера

MyIntU = MyIntU + (int)3.14159;

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


[ Назад | Оглавление | Далее ]









helloworld.ru © 2001-2021
Все права защищены