OpenSCADAWiki:
Roman Savochenko
/
C Short All
/
part1
/part4
...
Home
|
Index
|
Changes
|
Comments
|
Users
|
Registration
|
Login
:
Password:
====1.4 Синтаксис==== =====1.4.1 Полезные обороты===== * Приведение типов: %%(php) long с = (long)a; - традиционная запись; long с = long(a); - функциональная запись; %% * Декларация нескольких переменных одного типа: %%(php)int x, // x y, // y z; // z%% * Варианты использования параметров функций: * для меняющихся аргументов необходимо использовать ссылки или указатели (ссылки на массив); //int test(int *ptr, int &alias, int[] &mass );// * для неизменяемых аргументов использовать прямую передачу по значению ; //int test(int value);// * для больших неизменяемых аргументов использовать константные ссылки или указатели на константные данные; //int test(const int &value, const int *ptr);// * Использование ключевого слова const (запрет модификации): * неконстантный указатель на неконстантные данные; //void test(char *str);// * неконстантный указатель на константные данные; //void test(const char *str);// * константный указатель на неконстантные данные; //int * const ptr = &x;// * константный указатель на константные данные; //const int * const ptr = &x;// * константный класс - не позволяет запускать неконстантные функции члены, кроме конструктора и деструктора; //const Time moon(12,0,0);// * константная функция - недопускется ничего (кроме mutable членов) модифицировать в константных функциях, а также вызывать неконстантные функции; //int getValue() const;// * Предотвращение многократного включения заголовочных файлов: %%(php)#ifndef TEST_H #define TEST_H <code> #endif%% * Комментирование/исключение больших кусков кода: %%(php)#if 0 <code> #endif%% * Использование значений параметров функций по умолчанию: %%(php)void show_values(int one=1, int two=2, int three=3); show_value(); show_value(23);%% * Объявление переменных по месту: %%(php)for (int count = 0; count < 10;count++)%% * Функции переменного числа параметров: %%(php)void text(parm x,char *fmt, ...) { char str[100]; va_start (argptr,fmt); vsprintf(str,fmt,argptr); va_end(argptr); printf(str); } text(54,"hello %s","world");%% * Указание способа(языка) для которого должна компилироваться функция: %%(php)extern "C" func(); // В стиле "C" extern "C++" func(): // В стиле "C++" extern "C++" { int func(void); }%% =====1.4.2 Указатели===== Особенностью языка ~С/С++ является возможность доступа к переменной не только по имени но и с использованием механизма указателей. Для этого в языке предусмотрены символы: "&" и "*". Символ "*" используется для индикации переменной (*ptr), которая расположена в памяти по адресу на который указывает одноимённая переменная без звёздочки. Символ "&" используется как для определения адреса ячейки памяти переменной, так и для определения адреса указателя на переменную. * Назначение адреса указателя: %%(php)int *ptr = (int *)0x0010; //при инициализации ptr = (int *)0x0010; //в программе%% * Присвоение значения непосредственно переменной на которую указывает указатель: %%(php)*ptr = 300%% * Родовой указатель в ~С/С++ основан на использовании указателя типа (void *). Ключевое слово void говорит об отсутствии данных о размере объекта в памяти. Во всех случаях использования указателя описанного как void*, необходимо выполнять операцию явного приведения типа указателя: %%(php)unsigned long block = 0xffeeddccL; void *ptr = █ unsigned char = *(unsigned char *)ptr; long int four_bytes = *(long int *)ptr;%% * Определение адреса указателя: %%(php)int *ptr; k = &ptr;%% * Указатель на указатель: %%(php)int data = 5; int *ptr = &data; // ptr[0]==5; int **ptr1 = &ptr; // ptr1[0][0]==5; int ***ptr2 = &ptr1; // ptr2[0][0][0]==5;%% * Возврат указателя функцией: %%(php)bool *cimpare(int, int);%% * Указатель на функцию: %%(php)bool (* compare)(int, int);%% * Указатели на члены класса (.* и ->*) %%(php)class Test { public: void funct() { cout << "Функция\n"; } int value; }; Test t; Test *tPtr = &t; void (Test::*memPtr)() = &Test::funct; int Test::*vPtr = &Test::value; (tPtr->*memPtr)(); //косвенный вызов функции cout << (*tPtr).*vPtr << endl;%% =====1.4.3 Ссылки (C++)===== Ссылка являются псевдонимом (алиасом) от переменной на которую она ссылается. При изменении ссылаемой переменной изменяется ссылка. В основном ссылки используются при описании параметров функций и указывают что переменная может меняться. %%(php) int &test(int &x); int data = 5; int &al_data = data; // al_data == 5; al_data = 10; // data == 10; data = 7; // al_data == 7;%% =====1.4.4 Массивы===== Как и в других языках, ~С/С++ поддерживает массивы которые тесно переплетаются с указателями. Элементы массива имеют один и тот же тип и расположены в памяти друг за другом. Имя массива также можно воспринимать как указатель на начало массива. В отличие от других языков в ~С/С++ отсутствует специальный строковый тип. Вместо него строковые литералы представляются как одномерный массив элементов типа char оканчивающегося символом "0". * Явное указание числа элементов массива и списка начальных значений: %%(php)char array[] = {'A','B','C','D',0}; char array[] = "ABCD"; char array[5] = {'A','B','C','D',0}; char *string = "ABCD"; string = "ABCD";%% * Обращение к элементам массива с помощью указателя: %%(php)*(array+i); array[i][j]; *(array[i]+j); *(*(array+i)+j);%% * Многомерные массивы: %%(php)matrix[2] == &matrix[2][10]; long (* matrix1)[3][2][4]; matrix1 = new long[3][2][4]; char *messages[20] == char messages[20][80]); char string[][80]= { "Первая строка", "Вторая строка", "Следующая строка" }; int m[][3] = { {00}, {10, 11}, {20, 21, 22,} }; char *Names[]= { "Aleksey", "Vladislav", "Vitaly" };%% * Массив указателей на функцию: %%(php)int (* fcmp[5])(int) = {cmp_name, cmp_title, cmp_year, cmp_price, cmp_totaly}; void (* func[3])(int); //определение (* func[choice])(choice); //вызов%% =====1.4.5 Перегрузка функций===== В языке C++ разрешается иметь множество функций с одним и тем же именем, но отличающиеся типами параметров или их количеством: %%(php) int sum(int *array, int element) { } float sum(float *array, int element) { } %% =====1.4.6 Перегрузка операций===== Перегрузкой операция является процедура расширения функций существующих операция для новых типов x(объектов). Операции допускающие перегрузку указанны в табл.4 . При перегрузке операций их старшинство и ассоциативность не изменяется. * Унарная операция (префиксная). //Операция:// !S //Вызывает:// S.operator!() или operator!(S) //Объявляется:// bool operator!() const; или friend bool operator!(const String &); * Унарная операция (постфиксная). //Операция:// d1++ //Вызывает:// d1.operator++(0) или operator++(d1,0) //Объявляется:// Date::operator++(int); или friend Date::operator++(Date &,int); * Бинарная операция. //Операция:// y+=z //Вызывает:// y.operator+=(z) или operator+=(y,z) //Объявляется:// const String &operator+=(const String &); или friend const String &operator+=(String &, const String &); * Вызов функции. //Операция:// string(2,2); //Вызывает:// string.operator()(2,2); //Объявляется:// String operator()(int,int); * Приведение типов. //Операция:// (char *)S; //Вызывает:// S.operator char*() //Объявляется:// String operator char*(); или String(char *); (конструктор неявного преобразования). * операция "new". //Операция:// ~Class1 *cls = new ~Class1; или ~Class1 *cls = new ("class") ~Class1; //Вызывает:// ~Class1 *cls = ~Class2.operator new(sizeof(~Class1)); или ~Class1 *cls = ~Class2.operator new("class", sizeof(~Class1)); //Объявляется:// void* ~Class2::operator new(size_t size); или void* ~Class2::operator new(string modul, size_t size); * операция "delete". //Операция:// delete cls; //Вызывает:// ~Class2.operator delete(cls); //Объявляется:// void* ~Class2::operator delete(void *addr); Таблица 4. **Операции допускающие перегрузку** #| ||+|-|*|/|%|^|&|||| ||~|!|=|<|>|+=|-=|*=|| ||/=|%=|^=|&=||=|<<|>>|>>=|| ||<<=|==|!=|<=|>=|&&||||++|| ||--|->*|,|->|[]|()|new|delete|| ||new[]|delete[]|| |# =====1.4.7 Шаблоны===== Шаблоны определяются с помощью ключевого слова **template** и предназначены для определения функций и классов способных работать с различными типами входных и выходных параметров. Шаблоны и наследование связаны следующим образом: * шаблон класса может быть производным от шаблонного класса; * шаблон класса может являться производным от нешаблонного класса; * шаблон класса может быть производным от шаблона класса; * нешаблонный класс может быть производным от шаблона класса. Шаблонные классы: * Объявление: %%(php)template <class Templ> class Tree { public: Tree( const Templ& n ); insertN(const Templ &); } template <class Templ> Tree<Templ>::Tree(const Templ& n) { };%% * Использование: %%(php)Tree<int> NewTree(23); Tree<float> NewTree(56.8);%% Шаблонные функции: * Объявление: %%(php)template <class T> // или template <typname T>; T max(T val1, T val2, T val3) { T max = val1; if(val2 > max) max=val2; if(val3 > max) max=val3; return max; }%% * Использование: %%(php)int rez = max(1,10,3); float rez = max(0.5,9.99,6.78);%% Шаблоны и друзья: %%(php) friend void f1(); //друг любого класса friend void f2(x<T> &); //друг конкретного класса friend void A::f4(); //друг любого класса friend void C<T>::f5(x<T> &); //друг конкретного класса friend class Y; //класс Y дружественен любому классу friend class Z<T>; //класс Y дружественен конкретному классу%% =====1.4.8 Обработка исключительных ситуаций===== В языке C++, добавлен мощный аппарат обработки исключительных ситуаций. Этот аппарат позволяет отлавливать как все типы исключений, так и конкретно взятый тип исключений. Так если записать catch(...), то будут отлавливаться все типы исключений. Кроме того обработка исключительных ситуаций оказываться вынесенной из "основной линии" выполнения программы. Для генерации повторных исключений в catch опускаться использование (throw) без параметров. Если происходит глубоковложенное исключение, то выполняется "раскрутка" стека для возвращения до ближайшего catch Обработка исключительных ситуаций описывается следующим образом: %%(php)try //начало блока испытания { if() throw MyType(); // Принудительная генерация } // (точка генерации) catch(MyType &Mt) {...}; // Отлов и обработка исключений My Type catch(...){...}; // Отлов и обработка всех остальных исключений%% Для ограничения круга генерируемых исключений функцией, можно указать спецификацию исключений для функции: %%(php) int g(double h) throw(a,b,c) //может генер. a,b,c и //unexpected int g(double h) throw() //не может генерировать //(кроме unexpected) int g(double h) //может генерировать все%% Стандартные обработчики исключений: * bad_alloc (exception) -- ошибка выделения памяти с помощью new; * bad_cast (exception) -- генерируется dynamic_cast; * bad_exception (exception) -- неожиданное исключение генерируется в случае неожиданного исключения при включении std::bad_exception в throw-список функции; * bad_typeid (exception) -- генерируется typeid; * invalid_argument (exception) -- функции передан недопустимый аргумент; * logic_error (exception) -- исключения в логических операциях; * length_error (exception) -- длина более максимально допустимой; * out_of_range (exception) -- аргумент вне допустимого диапазона; * runtime_error (exception) -- Ошибка в программе; * overflow_error (runtime_error) -- математическая ошибка переполнения сверху; * underflow_error (runtime_error) -- математическая ошибка переполнения снизу; Чтоб избежать утечек памяти, обусловленных забыванием вызова delete после new, можно использовать шаблон auto_ptr, который будет автоматически разрушаться. На базе класса exception, можно генерировать собственные исключения.
Please type the word you read in the image: