- •5.Препроцессор. Директивы препроцессора.
- •7.Работа с файлами. Текстовый и двоичный режим.
- •8.Указатели. Адресная арифметика.
- •10.Перечислимый тип. Структуры. Объединения.
- •11.Поразрядные операции.
- •13.Спецификаторы класса памяти.
- •14.Пространства имён.
- •15.Компоновка. Правило одного определения.
- •17.Функции-члены класса. Указатель this.
- •16.Понятие класса.
- •18.Конструкторы. Деструкторы.
- •19.Преобразования объектов класса.
- •20.Доступ к членам класса.
- •21.Статические члены класса.
- •22.Друзья класса.
- •23.Совместное использование.
- •24.Перегрузка операций.
- •25.Шаблоны.
- •26.Обработка исключительных ситуаций.
- •27.Производные классы.
- •28.Виртуальные функции. Абстрактные классы.
- •29.Указатели на члены класса.
- •30.Множественное наследование.
- •31.Структура dll-библиотеки.
- •32.Статическое и динамическое подключение dll-библиотек.
- •34.Регистры процессора.
- •35.Использование стека. Команды работы со стеком в языке ассемблера.
- •36.Арифметические команды в языке ассемблера.
- •37.Команды сравнения и перехода в языке ассемблера.
- •38.Команды работы с битами в языке ассемблера.
- •39.Процедуры в языке ассемблера. Передача параметров в процедуру.
- •40.Процедуры в языке ассемблера. Возврат результата. Локальные данные.
7.Работа с файлами. Текстовый и двоичный режим.
Работа с файлами FILE – спец структура, объявленная в файле <stdio.h>, которая используется при работе с файлами. Для работы с файлом нужно объявить переменную FILE *<имя>. Функция fopen используется для открытия файла. Первый параметр задаёт имя файла. Второй параметрmode задаёт требуемый тип доступа к файлу. Кроме того, к параметру mode могут быть добавлены символы t и b для задания текстового и двоичного режимов соответственно. По умолчанию используется текстовый режим. В случае ошибки функция fopen возвращает значение NULL.
Текстовый режим При вводе/выводе в текстовом режиме происходит преобразование между внешним представлением значения и внутренним (машинным) представлением этого значения.
Двоичный режим В двоичном режиме никаких преобразований не производится, внутреннее представление значения записывается в файл. Для открытия файла в двоичном режиме необходимо в параметр mode функции fopenдобавить символ b. Функция fread читает из файла file в переменную buf num элементов, каждый размером bytes байт. Функция fwrite записывает в файл file из переменной buf num элементов, каждый размером bytes байт. Функции возвращают количество прочитанных/записанных элементов. В двоичном режиме возможен прямой доступ к файлу:
int fseek(FILE *file, long nbytes, int origin). Данная функция смещает указатель в файле file на nbytes байт с позиции, определяемой параметромorigin. При этом параметр origin может принимать следующие значения:
SEEK_SET 0 – начало файла;
SEEK_CUR 1 – текущая позиция указателя;
SEEK_END 2 – конец файла.
Функция long ftell(FILE *file) возвращает текущую позицию указателя в файле file.
8.Указатели. Адресная арифметика.
Указатели
Каждая переменная, которую вы объявляете в программе, имеет адрес – номер ячейки памяти, в которой она расположена. Адрес является неотъемлемой характеристикой переменной. Можно объявить другую переменную, которая будет хранить этот адрес и которая называется указателем. Указатели применяются при передаче в функцию параметров, которые мы хотим изменить, при работе с массивами, при работе с динамической памятью и в ряде других случаев. Объявление указателя имеет следующий синтаксис: <тип> *<идентификатор> [ = <инициализатор>];
Указатель может указывать на значения базового, перечислимого типа, структуры, объединения, функции, указателя. В последнем объявлении для формирования типа используются два оператора: * и [ ], один из которых стоит перед именем, а другой – после. Использование операторов объявления значительно упростилось бы, будь они все либо префиксами, либо суффиксами. Однако, *, [] и () разрабатывались так, чтобы отражать их смысл в выражениях. Таким образом, * является префиксом, а [ ] и ( ) – суффиксами. Суффиксные операторы «крепче связаны» с именем, чем префиксные. Следовательно, *names[ ] означает массив указателей на какие-либо объекты (char *names[] = {"John", "Anna"};), а для определения типов наподобие «указатель на функцию», необходимо использовать скобки.Существуют две операции, которые имеют отношение к работе с указателями. Этими операциями являются:
операция взятия адреса (адресация) &;
операция взятия значения по адресу (косвенная адресация или разыменование) *.
Указатель на void Специальное применение имеют указатели на тип void. Указатель на тип void может указывать на значения любого типа. Однако для выполнения операций над указателем на void либо над указуемым объектом, необходимо явно привести тип указателя к типу, отличному от указателя на void. Указатель на объект любого типа можно присвоить переменной типа void*, один void* можно присвоить другому void*, пару void* можно сравнивать на равенство и неравенство, и, наконец, void* можно явно преобразовать в указатель на другой тип. Чтобы воспользоваться void*, необходимо явно преобразовать его в указатель определённого типа( void f(int *pi) void *pv = pi;(неявн) или int *pi2 = static_cast<int*>(pv);(явн)). Основными применениями void * являются передача указателей функциям, которым не позволено делать предположения о типе объектов, а равно возврат объектов «неуточненного» типа из функций. Чтобы воспользоваться таким объектом, необходимо явно преобразовать тип указателя.
Ноль Ноль имеет тип int. , его можно использовать в качестве константы любого интегрального типа, типа с плавающей точкой и указателя. Тип нуля определяется по контексту. Ноль, как правило представлен в виде последовательности нулевых битов соответствующей длины.Следовательно, указатель, равный нулю, можно интерпретировать как указатель, который ни на что не ссылается.
Указатели и константы Для объявления указателя в качестве константы, используется оператор объявления * const, а не просто *( void f(char *p) char s[] = "const"; const char *p1 = s;(указ на конст) или char * const p2 = s; (конст-й указ) или const char * const p3 = s; (конст указ на конст)).
Можно присвоить адрес переменной указателю на константу, потому что это безвредная операция. Нельзя, однако, присвоить адрес константы произвольному указателю, потому что в этом случае можно было бы изменить значение константного объекта.
Адресная арифметика Над указателями можно производить следующие действия:
складывать указатель и целое число;
вычитать из указателя целое число;
вычитать из указателя указатель – получается целое число.
При этом прибавляемое/вычитаемое или полученное целое число обозначает количество элементов того типа, на который указывает указатель, т.е. это число умножается или делится на размер типа.Вычитание указателей друг из друга определено только в том случае, если оба указателя указывают на элементы одного и того же массива. Результатом вычитания одного указателя из другого будет количество элементов массива между этими указателями. В результате прибавления целого числа к указателю и вычитания целого числа из указателя получается новый указатель. Указатели можно использовать для обработки массивов.Из того, что можно вычитать из указателя целое число, следует, что возможно использование отрицательных чисел в операции [ ].
Указатели на функции Указатель, полученный взятием адреса функции, можно затем использовать для вызова функции(void f(int x) { ... } void (*pf)(int); void g() { pf = &f; pf(0); }).Компилятор распознаёт, что pf является указателем и вызывает функцию, на которую он указывает. То есть, разыменование указателя на функцию при помощи операции * необязательно;необязательно пользоваться операцией & для получения адреса функции.Параметры указателей на функцию объявляются точно так же, как и параметры самих функций(typedef void (*PF)(int); PF pf;). При присваивании типы функций должны в точности совпадать.Правила передачи параметров при вызове функций через указатель те же самые, что и при непосредственном вызове функций.Ссылка - это объект, который синтаксически выглядит как переменная, а по семантике является адресом. Объявление ссылки, кроме случаев, когда ссылка является параметром функции, возвращаемым функцией значением или членом класса, должно содержать инициализатор(int &r = a;). Далее все операции производятся не над самой ссылкой, а над тем объектом, на который она указывает. ссылка является удобной заменой указателю, но она затрудняет понимание программы из-за несовпадения синтаксиса и семантики ссылки. Однако ссылки могут быть полезны для того, чтобы не передавать по значению (и не копировать) параметр функции, который имеет большой размер. В том случае, если мы не собираемся менять этот параметр внутри функции, можно объявить ссылку с модификатором const. В этом случае мы будем гарантированы, что параметр не изменится, вместо большого объекта будет передаваться его адрес, а для пользователя всё будет выглядеть как передача параметра по значению(class X { ... }; int f (const X& x) { ... }).
9.Строки в языке С++.
Строка – это последовательность (массив) символов (типа char), которая заканчивается специальным символом – признаком конца строки '\0' и равен 0. При вводе строки символ конца строки добавляется автоматическиЕсли требуется сформировать новую строку, то обязательно надо добавлять признак конца строки(char str[51];).Строковым литералом(“a”) называется последовательность символов, заключённых в двойные кавычки. В строковом литерале на один символ больше, чем используется при его записи – добавляется символ '\0'.Тип строкового литерала есть «массив с надлежащим количеством константных символов». Строковый литерал можно присвоить переменной типа char *. Однако изменение строкового литерала через такой указатель является ошибкой.строковые литералы являются константами.Если же нужна строка, которую можно модифицировать, следует объявить и инициализировать массив символов(char str[] = "С & С++"; str[2] = '?';).Память под строковые литералы выделяется статически, поэтому их можно возвращать в качестве значения функции.Поскольку мы не знаем, сколько в строке содержится символов, но знаем, что в конце стоит символ конца строки, цикл для обработки строки пишется следующим образом: for (int i = 0; str[i] != '\0'; i++) { ... }.Можно опустить сравнение с нулем, для C++ это будет эквивалентно: for (int i = 0; str[i]; i++) { ... }.Можно использовать указатели для обработки строк: char str[50], *p; ... for (p = str; *p; p++) { ... }. Заголовки стандартных функций работы со строками хранятся в файле <string.h>. Основными из этих функций являются:
Определение длины строки– int strlen(const char *str);
Сравнение строк– int strcmp(const char *str1, const char *str2);
Копирование – char *strcpy(char *str1, const char *str2);
Конкатенация строк – char *strcat(char *str1, const char *str2);
Поиск символа в строке – char *strchr(const char *str, char c);
Поиск подстроки – char *strstr(const char *str1, const char *str2);
Ввод/вывод строки:
Ввод строки до пробела или другого разделителя – функция scanf с форматом %s;
Ввод строки, содержащей пробелы – char *gets (char *buffer);
Ввод строки из файла, n задаёт максимальное количество символов для ввода – char *fgets(char *string, int n, FILE *stream);
Вывод строки с форматированием – функция printf с форматом %s;
Вывод строки – int puts(const char *string);
Вывод строки в файл – int fputs(const char *string, FILE *stream);
