Многофайловые проекты
Рано или поздно, но проект разрастается и становится трудночитабельным, а также труднопереносимым в другие проекты, для упрощения работы используется разбиение «мега проекта» на несколько мелких, функционально законченных проектов.
Принцип в языках C/C++ примерно одинаков: создаются отдельные файлы с расширением .c/cpp для кода и файл заголовка .h для реализации.
Примечание 1: желательно все файлы с кодом хранить в папке src, а заголовочные в папке inc, можно отдельно прописать пути к файлам с исходниками, или указывать путь.
Для функций:
Создается файл sourse (файл с кодом/реализацией) имеющий расширение .c/.cpp
Например myfile.cpp
В нем напишем:
#include "inc\myfile.h" //если прописали пути, то #include "myfile.h"
void PrintHello()
{
std::cout<<"Hello World"<<std::endl;
}
и отдельно файл с объявлениями функций (header файл),например myfile.h
Внутри него напишем:
#ifndef MYFILE_H
#define MYFILE_H
#include //библиотека, требуемая для работы функции.
void PrintHello(); //прототип функции, ее реализация в файле myfile.cpp
#endif // MYFILE_H
Теперь в файле main.cpp мы можем подключить header файл
#include «inc\myfile.h»
И в функции main вызвать интересующую функцию:
int main()
{
PrintHello();
return 0;
}
Для классов:
В большинстве вред предусмотрено автоматическое создание файлов .cpp и h для классов + создание самого класса, что весьма удобно.
В случае с классом – в заголовочном файле нужно указывать его структуру, а реализацию методов выносить в .cpp файл
Например:
Header файл
#ifndef MYCLASS_H
#define MYCLASS_H
#include //библиотека, требуемая для работы функции.
class MyClass
{
public:
MyClass();
void PrintMsg();
};
#endif // MYCLASS_H
Файл с реализацией:
#include "myclass.h"
MyClass::MyClass(){}
void MyClass::PrintMsg()
{
std::cout<<"Hello World from MyClass"<<std::endl;
}
Теперь в файле main.cpp мы можем подключить header файл, создать объект класса и вызвать метод.
int main()
{
MyClass a;
a.PrintMsg();
return 0;
}
Использование пространства имен:
Мы можем использовать пространства имен чтобы разграничить функции/классы с одинаковыми названиями.
Для этого в .cpp и .h файлах требуемые фрагменты кода и реализаций помещаем внутри конструкции
namespace Myname
{
//код или реализация
}
Примечание 2:
В языке C нет функционала класса, но часто требуется работать с одними и теми же переменными в разных классах, для этого можно в .h файле создавать прототип (структуры/объединения) в файле с кодом создать переменную/структуру/объединение, а в файле .h создать extern для этого «объекта»
Примечание 3:
Как можно было заметить, в заголовочных файлах присутствует «странная» конструкция
#ifndef MYFILE_H
#define MYFILE_H
#endif // MYFILE_H
Она нужна для защиты от многократного включения одного и тогоже фрагмента кода в проект.
Директивы описанные выше воспринимаются любыми компиляторами и средами разработки, в более современных применяется директива препроцессора
#pragma once
Важно отметить, что допускается применение 2-х директив одновременно, хоть 1 из них, но сработает.