Допустим, у нас есть add.h add.cpp и main.cpp.
Вам нужен прототип add как в main.cpp, так и в add.cpp. Это нужно main.cpp, потому что он хочет использовать класс add, а это нужно add.cpp, потому что он хочет реализовать его, поэтому нужен его прототип. Это делается, как вы знаете, путем включения файла заголовка.
Выполнение #include «add.h» в add.cpp и main.cpp.
Теперь компилятор вступает в действие, создает два объектных файла, а именно main.o и add.o. Так что пока главный знает только о add, внутренней механики (реализации) еще нет. После этого компоновщик объединяет main.o и add.o в исполняемый файл, в котором есть все навороты и свистки, которые запускает add из main.
После компиляции каждый объектный файл знает по имени. После связывания они фактически знают, как назвать их по имени (где он (реализация) живет.
Перед компилятором у нас есть еще один шаг, который называется предварительной обработкой. На этом шаге выполняется копирование содержимого файлов после # include.
Независимо от того, как вы называете add.h, это не имеет значения, но вы должны включить правильный файл в main.cpp и add.cpp. Независимо от того, как вы вызываете add.cpp или main.cpp, не имеет значения, только ваш компилятор должен быть проинструктирован о том, как они вызываются. Например, в Visual Studio это делается автоматически, переименовывая их в файле проекта. Если вы используете gcc, вы должны сами указать свой компилятор и компоновщик В этой конкретной ситуации вы делаете следующее.
скомпилируйте add.cpp в add.o:
gcc -c add.cpp
скомпилировать main.cpp в main.cpp:
gcc -c main.cpp
ссылка add.o и main.o в myniceprogram:
gcc -o myniceprogram add.o main.o