Первое знакомство с С++
Первое знакомство с С++
Программа С++ состоит из одной или нескольких единиц компиляции. Каждая единица компиляции представляет собой отдельный файл исходного кода, обычно имеющий расширение .cpp (другими распространенными расширениями являются .cc и .cxx); она обрабатывается компилятором за один шаг. Для каждой единицы компиляции компилятор генерирует объектный файл с расширением .obj (в Windows) или .о (в Unix и Mac OS X). Объектный файл — это бинарный файл, содержащий машинный код для той архитектуры, на которой будет выполняться программа.
После компиляции всех файлов .cpp мы можем собрать все объектные файлы для создания исполняемого модуля, используя специальную программу, называемую компоновщиком (linker). Компоновщик соединяет объектные файлы в единое целое и назначает адреса памяти функциям и другим символическим ссылкам, которые содержатся в единицах компиляции.
Рис. Б.1. Процесс компиляции программы на С++ (в Windows).
При создании программы только одна единица компиляции должна иметь функцию main(), которая является точкой входа в программу. Эта функция не принадлежит никакому классу — она является глобальной функцией.
В отличие от Java, где каждый исходный файл должен содержать точно один класс, С++ позволяет организовать единицу компиляции удобным для нас способом. Можно реализовать несколько классов в одном файле .cpp или распространить реализацию класса на несколько файлов .cpp; имена исходных файлов могут быть любыми. При внесении изменений в один конкретный файл .cpp потребуется перекомпилировать этот файл и затем повторно скомпоновать приложение для создания нового исполняемого модуля.
Прежде чем мы пойдем дальше, давайте рассмотрим очень простую программу на С++, вычисляющую квадрат целого числа. Эта программа состоит из двух единиц компиляции: main.cpp и square.cpp.
Ниже показан файл square.cpp:
01 double square(double n)
02 {
03 return n * n;
04 }
Этот файл содержит лишь глобальную функцию с именем square(), которая возвращает квадрат своего параметра.
Ниже показан файл main.cpp:
01 #include <cstdlib>
02 #include <iostream>
03 using namespace std;
04 double square(double);
05 int main(int argc, char *argv[])
06 {
07 if (argc != 2) {
08 cerr << "Usage: square <number>" << endl;
09 return 1;
10 }
11 double n = strtod(argv[1], 0);
12 cout << "The square of " << argv[1] << " is " << square(n) << endl;
13 return 0;
14 }
Исходный файл main.cpp содержит определение функции main(). В С++ эта функция принимает в качестве параметров int и char * (массив символьных строк). Имя программы находится в argv[0], а аргументы командной строки — в argv[1], argv[2], … argv[argc — 1]. Параметры имеют стандартные имена argc («argument count» — количество аргументов) и argv («argument values» — значения аргументов). Если программа не использует аргументы командной строки, функцию main() можно определить без параметров.
Функция main() использует из стандартной библиотеки С++ функции strtod() («string to double» — преобразование строки в переменную двойной точности), cout (стандартный поток вывода С++) и cerr (стандартный поток вывода сообщений об ошибках С++) для преобразования аргумента командной строки в тип double и для вывода текста на консоль. Строки, числа и маркеры конца строки (endl) выводятся с помощью оператора <<, который также используется для сдвига битов. Чтобы воспользоваться этой стандартной функциональностью, необходимо включить директивы #include, расположенные в строках 1 и 2.
Директива using namespace в строке 3 указывает компилятору на то, что мы хотим импортировать в глобальное пространство имен все идентификаторы, объявленные в пространстве имен std. Это позволяет нам пользоваться записью strtod(), cout, cerr и endl вместо указания полных имен: std::strtod(), std::cout, std::cerr и std::endl. В С++ оператор :: разделяет компоненты сложного имени.
В строке 4 объявляется прототип функции. Он указывает компилятору на то, что существует функция с данными параметрами и возвращаемым значением. Реальное определение функции может находиться в той же или в другой единице компиляции. Без прототипа функции компилятор не позволил бы нам вызвать эту функцию в строке 12. Имена параметров функции указывать необязательно.
Процедура компиляции программы зависит от платформы. Например, для компиляции программы в Solaris с использованием компилятора С++ компании «Sun» мы могли бы задать следующие команды:
CC -с main.cpp
CC -с square.cpp
ld main.o square.o -о square
Первые две строки вызывают компилятор, чтобы сгенерировать файлы .о для соответствующих файлов .cpp. Третья строка вызывает компоновщик и формирует исполняемый модуль с именем square, который может запускаться следующим образом:
./square 64
Эта программа выводит на консоль следующее сообщение:
The square of 64 is 4096
(Квадрат числа 64 равен 4096)
Чтобы скомпилировать программу, вы, возможно, попросите помощи у местного опытного программиста С++. Если это не удастся сделать, можете прочитать остальную часть приложения, ничего не компилируя, и воспользоваться инструкциями в главе 1 по компиляции вашего первого приложения C++/Qt. В Qt предусмотрены утилиты, позволяющие легко создавать приложения на любой платформе.
Вернемся к нашей программе. В реальном приложении, как правило, мы размещали бы прототип функции square() в отдельном файле и включали бы этот файл во все единицы компиляции, в которых вызывается эта функция. Такой файл называется заголовочным; он обычно имеет расширение .h (часто встречаются также расширения .hh, .hpp и .hxx). Если переделать наш пример, используя заголовочный файл, то можно было бы создать файл с именем square.h, который содержит следующие строки:
1 #ifndef SQUARE_H
2 #define SQUARE_H
3 double square(double);
4 #endif
В начале и в конце заголовочного файла задаются препроцессорные директивы (#ifndef, #define и #endif). Эти директивы гарантируют однократное выполнение заголовочного файла, даже если он несколько раз включается в одну и ту же единицу компиляции (такая ситуация возникает, когда одни заголовочные файлы включают в себя другие заголовочные файлы). По принятым соглашениям используемый для этого препроцессорный символ строится на основе имени файла (в нашем примере это символ SQUARE_H). Позже в этом приложении мы вернемся к рассмотрению препроцессора.
Новый файл main.cpp будет иметь следующий вид:
01 #include <cstdlib>
02 #include <iostream>
03 #include "square.h"
04 using namespace std;
05 int main(int argc, char *argv[])
06 {
07 if (argc != 2) {
08 cerr << "Usage: square <number>" << endl;
09 return 1;
10 }
11 double n = strtod(argv[1], 0);
12 cout << "The square of " << argv[1] << " is " << square(n) << endl;
13 return 0;
14 }
Используемая в строке 3 директива #include разворачивает содержимое файла square.h. Директивы, начинающиеся с символа #, рассматриваются препроцессором С++ до фактической компиляции. В прежние дни препроцессор являлся отдельной программой, которую программист вызывал вручную перед выполнением компилятора. В современных компиляторах этап препроцессорной обработки выполняется автоматически.
Директивы #include в строках 1 и 2 разворачивают содержимое заголовочных файлов cstdlib и iostream, которые являются частью стандартной библиотеки С++. Стандартные заголовочные файлы не имеют суффикса .h. Угловые скобки вокруг имен файлов говорят о том, что заголовочные файлы располагаются в стандартном месте системы, в то время как кавычки заставляют компилятор просматривать текущий каталог. Директивы #include обычно собирают вместе и располагают в верхней части файла .cpp.
В отличие от файлов .cpp, заголовочные файлы сами по себе не являются единицей компиляции и не приводят к созданию объектных файлов. Они могут только содержать объявления, позволяющие различным единицам компиляции взаимодействовать друг с другом. Следовательно, было бы неправильно помещать реализацию функции square() в какой-нибудь заголовочный файл. Если бы мы это сделали в нашем примере, ничего плохого не случилось бы, потому что square.h включается только однажды, однако если бы мы включали square.h в несколько файлов .cpp, то получили бы несколько реализаций функции square() (по одной на каждый файл .cpp, который включает этот заголовочный файл). После этого компоновщик пожаловался бы на существование нескольких (идентичных) определений функции square() и отказался бы генерировать исполняемый модуль. И наоборот, если мы объявляем функцию, но нигде ее не реализуем, компоновщик пожалуется на наличие «неразрешенного символа».
До сих пор мы предполагали, что исполняемый модуль состоит только из объектных файлов. На практике они компонуются также с библиотеками, которые реализуют готовую функциональность. Существует два основных типа библиотек:
• статические библиотеки непосредственно помещаются в исполняемый модуль, как будто они являются объектными файлами. Это гарантирует невозможность потери библиотеки, но увеличивает размер исполняемого модуля;
• динамические библиотеки (называемые также совместно используемыми библиотеками или библиотеками DLL) располагаются в стандартном месте на машине пользователя и автоматически загружаются во время запуска приложения.
Программу square мы компонуем со стандартной библиотекой С++, которая реализована как динамическая библиотека на большинстве платформ. Сами средства разработки Qt представляют собой коллекцию библиотек, которые могут создаваться как статические или как динамические библиотеки (по умолчанию они создаются как динамические библиотеки).
Более 800 000 книг и аудиокниг! 📚
Получи 2 месяца Литрес Подписки в подарок и наслаждайся неограниченным чтением
ПОЛУЧИТЬ ПОДАРОКЧитайте также
Первое знакомство с программой
Первое знакомство с программой Для запуска программы Extra Hide Studio можно использовать соответствующую команду программной папки Пуск ?
Первое знакомство с Internet Explorer
Первое знакомство с Internet Explorer Открывшееся окно обозревателя Интернета (рис. 5.6) очень похоже на окно Проводника – можно сказать, близнецы-братья.После запуска браузера на экране, как правило, начинает загружаться веб-страница. У меня, например, загрузилась страница
1. Первое знакомство с Windows Vista
1. Первое знакомство с Windows Vista Все редакции Windows Vista (от Starter до Ultimate) поставляются на одном лицензионном DVD. По замыслу Microsoft это позволит клиентам быстрее переходить на более продвинутые варианты новой операционной системы. В любое время пользователи смогут установить на
Глава 1. Первое знакомство
Глава 1. Первое знакомство В данной главе показано на примере создания простого приложения с графическим интерфейсом пользователя (GUI — graphical user interface), как можно обычные средства С++ совместить с функциональными возможностями Qt. Здесь также рассматриваются две ключевые
Первое знакомство с Qtopia
Первое знакомство с Qtopia Приложения Qtopia Core могут разрабатываться на любой платформе, позволяющей запускать цепочки многоплатформенных инструментальных средств. Наиболее распространено построение кросс-компилятора GNU С++ в системе Unix. Этот процесс упрощается благодаря
Первое знакомство с С++
Первое знакомство с С++ Программа С++ состоит из одной или нескольких единиц компиляции. Каждая единица компиляции представляет собой отдельный файл исходного кода, обычно имеющий расширение .cpp (другими распространенными расширениями являются .cc и .cxx); она обрабатывается
КОМПАС-3D V10: первое знакомство
КОМПАС-3D V10: первое знакомство Любой современный графический редактор обладает достаточно сложным интерфейсом. Как правило, конструкторские системы, представленные сегодня на рынке САПР, развиваются уже не один год. Они успели за это время накопить множество различных
1.2. Редактор VBA. Первое знакомство
1.2. Редактор VBA. Первое знакомство Запуск редактора VBAКак и любые среды программирования, редактор VBA необходимо сначала запустить. Для запуска можно использовать два способа:1) активизировать любое приложение пакета MS Office (Word, Excel);2) выполнить команду меню: Сервис + Макрос +
Первое знакомство с Microsoft PowerPoint 2007
Первое знакомство с Microsoft PowerPoint 2007 Чтобы запустить программу Microsoft Power Point 2007, выполните команду Пуск ? Все программы ? Microsoft Office ? Microsoft Office PowerPoint 2007. В результате откроется окно приложения, изображенное на рис. 4.1. Рис. 4.1. Интерфейс программы PowerPoint 2007Это главный рабочий
Первое знакомство с программой
Первое знакомство с программой Чтобы запустить программу, выполните команду Пуск ? Все программы ? Microsoft Office ? Microcoft Office Access 2007 или дважды щелкните кнопкой мыши на соответствующем ярлыке Рабочего стола. В результате откроется окно, изображенное на рис. 6.1. Рис. 6.1. Окно
Указатели: первое знакомство
Указатели: первое знакомство Указатели? Что это такое? Вообще говоря, указатель - некоторое символическое представление адреса. Например, ранее мы воспользовались операцией получения адреса для нахождения адреса переменной pooh. В данном случае &pooh означает
Первое знакомство с меню цифровой камеры
Первое знакомство с меню цифровой камеры Итак, камера включена, а ее операционная система загружена. Теперь можно настроить фотоаппарат. Элементов управления у него немного, и большинство функций и настроек доступны только через меню. Изменить настройки вы можете,
Урок 1.1. Первое знакомство с компьютером
Урок 1.1. Первое знакомство с компьютером Что такое компьютер Наверное, очень трудно найти человека, который никогда не видел компьютер. Однако очень многие люди не могут дать четкое определение, что же это такое. Еще лет 20 назад компьютером называли электронное
Первое знакомство с Internet Explorer 7
Первое знакомство с Internet Explorer 7 Для просмотра размещенных в Интернете веб-страниц служат браузеры (обозреватели) – специальные программы, умеющие загружать веб-страницы на ваш компьютер, отображать их и выполнять переходы по ссылкам. В состав Windows Vista входит седьмая