Форум программистов, компьютерный форум, киберфорум
С++ для начинающих
Войти
Регистрация
Восстановить пароль
Блоги Сообщество Поиск Заказать работу  
 
Рейтинг 4.90/29: Рейтинг темы: голосов - 29, средняя оценка - 4.90
Велосипедист...
 Аватар для Mournful Max
353 / 220 / 73
Регистрация: 15.12.2015
Сообщений: 785

Многофайловый проект

27.03.2017, 03:22. Показов 5516. Ответов 11
Метки нет (Все метки)

Студворк — интернет-сервис помощи студентам
Здравия всем! Опять зеленый метушится!

Перед, непосредственно, главным вопросом, хочу показать то, что мне известно (если я не заблуждаюсь).
Если обобщить, понимаю, что есть следующие 3 основных этапа сборки программы:
1) препроцессирование;
2) компиляция;
3) линковка.
Как работает препроцессор, мне известно (или, по крайней мере, имею понятие). Представление компиляции и линковки тоже имеется.

Не знаю как правильно задать вопрос, поэтому попытаюсь привести пример в коде.
Вот, у нас есть book.cpp-файл с таким содержимым:
C++
1
2
#include "book.h"
int foo() { return 42; }
И, book.h-файл выглядит вот так:
C++
1
2
3
4
#ifndef _BOOK_H_
#define _BOOK_H_
int foo();
#endif
Теперь я решил написать программу, которая бы использовала функцию, определенную в book.cpp:
C++
1
2
3
4
5
6
7
8
9
// main.cpp
#include "book.h"
 
int main()
{
  int existence = foo();
 
  return 0;
}
Все скомпилировалось, все отлично, все довольны (кроме меня).

Вот что меня интересует: директива препроцессора include берет все содержимое из файла book.h и вставляет в main.cpp. Но в book.h содержится только лишь объявление функции foo(), а не ее реализация. Каким образом функция вызывается, если в коде ее нет?

Если возможно, объясните на уровне "день -- это когда видишь, ночь -- это когда не видишь"
0
IT_Exp
Эксперт
34794 / 4073 / 2104
Регистрация: 17.06.2006
Сообщений: 32,602
Блог
27.03.2017, 03:22
Ответы с готовыми решениями:

Многофайловый проект
Всем привет, уже довольно долго пытаюсь собрать проект из трех файлов: заголовочный, файл реализации функций, главный файл с вызовом...

Многофайловый проект
Доброго времени суток. В проекте 4 файла. Почему при первом варианте все работает, а во втором нет? // main.cpp #include...

Многофайловый проект в VS
Всем привет. Добавил новый элемент .cpp в свой проект, в котором уже есть другой .cpp, и компилятор отказывается компилировать новый...

11
Любитель чаепитий
 Аватар для GbaLog-
3745 / 1801 / 566
Регистрация: 24.08.2014
Сообщений: 6,020
Записей в блоге: 1
27.03.2017, 05:49
Лучший ответ Сообщение было отмечено Captain Maxee как решение

Решение

Вот тут, вроде, толково расписано.
https://habrahabr.ru/post/150327/
2
nd2
3438 / 2817 / 1249
Регистрация: 29.01.2016
Сообщений: 9,427
27.03.2017, 12:31
Процесс компиляции
1
Форумчанин
Эксперт CЭксперт С++
 Аватар для MrGluck
8216 / 5047 / 1437
Регистрация: 29.11.2010
Сообщений: 13,453
27.03.2017, 13:29
Лучший ответ Сообщение было отмечено Captain Maxee как решение

Решение

Цитата Сообщение от Captain Maxee Посмотреть сообщение
директива препроцессора include
Простая как палка, тупо вставляет весь текст, то есть после работы препроцессора в main.cpp будет
C++
1
2
3
4
5
6
7
8
9
10
11
12
// main.cpp
#ifndef _BOOK_H_
#define _BOOK_H_
int foo();
#endif
 
int main()
{
  int existence = foo();
 
  return 0;
}
Цитата Сообщение от Captain Maxee Посмотреть сообщение
Каким образом функция вызывается, если в коде ее нет?
Об этом заботится линкер. Для компилятора же важно лишь чтобы было видно определение класса/функции. А уж где это находится - в соседнем файле, либе и т.д. - дело компоновщика.
1
Велосипедист...
 Аватар для Mournful Max
353 / 220 / 73
Регистрация: 15.12.2015
Сообщений: 785
28.03.2017, 22:22  [ТС]
MrGluck,
Цитата Сообщение от MrGluck Посмотреть сообщение
Об этом заботится линкер. Для компилятора же важно лишь чтобы было видно определение класса/функции. А уж где это находится - в соседнем файле, либе и т.д. - дело компоновщика.
-- это стало понятно, после прочтения статей, которые скинули уважаемые nd2 и GbaLog-.
Непонятно осталось следующее: что же будет, если существует два .cpp-файла:
C++
1
2
3
// book1.cpp
#include "book.h"
int foo() { return 42; }
C++
1
2
3
// book2.cpp
#include "book.h"
int foo() { return -42; }
И book.h-файл:
Цитата Сообщение от Captain Maxee Посмотреть сообщение
C++
1
2
3
4
#ifndef _BOOK_H_
#define _BOOK_H_
int foo();
#endif
Что произойдет здесь?
Цитата Сообщение от Captain Maxee Посмотреть сообщение
C++
1
2
3
4
5
6
7
8
9
// main.cpp
#include "book.h"
 
int main()
{
  int existence = foo();
 
  return 0;
}
Если ошибка при компиляции (что-то вроде "Больше одного определения функции foo(void)), то появляется такой вопрос: линкер "заглядывает" в тот .cpp-файл, где есть строка #include "book.h"?

Скрыто, во имя сохранности пока положительной репутации самого меня
Ребята, я понимаю как сейчас я выгляжу в ваших глазах, но я очень дотошный педант, если за что-то берусь, то хочу понять до конца (если это возможно (ибо, в моем случае, познаю это только относительно)).
В моей картине сейчас такая каша: "Каким образом линкер выбирает реализацию функции foo из book.cpp, если в book.h лежит лишь объявление некой функции foo, без указания на файл book.cpp? Может, дело в самом файле book.cpp? Может, строчка с include все решает? Ведь может быть много файликов .cpp с реализацией функции foo... почему линкер выбирает именно book.cpp?"
0
nd2
3438 / 2817 / 1249
Регистрация: 29.01.2016
Сообщений: 9,427
28.03.2017, 22:27
Цитата Сообщение от Captain Maxee Посмотреть сообщение
линкер "заглядывает" в тот .cpp-файл, где есть строка #include "book.h"?
#include "book.h" можно убрать из файлов с реализациями функции, и ничего не изменится, линкеру он не нужен. Нужен от компилятору там, где есть вызовы функции.
1
Велосипедист...
 Аватар для Mournful Max
353 / 220 / 73
Регистрация: 15.12.2015
Сообщений: 785
28.03.2017, 22:36  [ТС]
nd2, Возьмем тот же код:
Цитата Сообщение от Captain Maxee Посмотреть сообщение
C++
1
2
// book1.cpp
int foo() { return 42; }
Цитата Сообщение от Captain Maxee Посмотреть сообщение
C++
1
2
// book2.cpp
int foo() { return -42; }
Цитата Сообщение от Captain Maxee Посмотреть сообщение
C++
1
2
3
4
5
6
7
8
9
// main.cpp
#include "book.h"
 
int main()
{
  int existence = foo();
 
  return 0;
}
То бишь, будет error с похожим объяснением: "Больше одного определения функции foo!"? Кажется, теперь я начинаю понимать, зачем нужны пространства имен.
0
-16 / 14 / 3
Регистрация: 22.01.2013
Сообщений: 154
28.03.2017, 22:42
Не, не так. Двойное определение, по-моему, к пространству имён не лепится.
0
nd2
3438 / 2817 / 1249
Регистрация: 29.01.2016
Сообщений: 9,427
28.03.2017, 22:43
Лучший ответ Сообщение было отмечено Captain Maxee как решение

Решение

Цитата Сообщение от Captain Maxee Посмотреть сообщение
Возьмем тот же код:
Возьмём.
Цитата Сообщение от Captain Maxee Посмотреть сообщение
То бишь, будет error с похожим объяснением: "Больше одного определения функции foo!"?
Будет. Линкер, в отличие от компилятора, видит все файла проекта.
1
Велосипедист...
 Аватар для Mournful Max
353 / 220 / 73
Регистрация: 15.12.2015
Сообщений: 785
28.03.2017, 22:57  [ТС]
nd2, Хм. Кажется, я понял!
Спасибо всем, ребята. Если есть какие-нибудь интересные плюшки, пишите, не стесняемся
0
-16 / 14 / 3
Регистрация: 22.01.2013
Сообщений: 154
28.03.2017, 23:17
Напиши оператор While.
0
Велосипедист...
 Аватар для Mournful Max
353 / 220 / 73
Регистрация: 15.12.2015
Сообщений: 785
28.03.2017, 23:19  [ТС]
gavrasio, рапорт на тебя напишу лучше. Заняться нечем больше?
0
Надоела реклама? Зарегистрируйтесь и она исчезнет полностью.
BasicMan
Эксперт
29316 / 5623 / 2384
Регистрация: 17.02.2009
Сообщений: 30,364
Блог
28.03.2017, 23:19
Помогаю со студенческими работами здесь

Многофайловый проект
Здравствуйте! Помогите создать Многофайловый проект. Пожалуйста. Создать абстрактный класс Figure с виртуальными методами...

Многофайловый проект
1й файл main.cpp #include <iostream> #include <locale> #include <Windows.h> #include "My_Struct.h" using namespace std; ...

Многофайловый проект
Собственно вопрос, скорее, к работе devc++ Ну вот захотел для "завтраки" собрать МП из 2 файлов 1 - main.cpp (ну как иначе) #include...

Многофайловый проект
Таки всеми правдами и неправдами создал из 3 файлов "тестик". И собственно не хочет это дело компилировать. Где я тут напортачил ? :( 1.)...

Многофайловый проект
Вот есть код. Помоги. Разбейте его на модуль. Я не понимаю как это сделать #include <iostream> using namespace std; int...


Искать еще темы с ответами

Или воспользуйтесь поиском по форуму:
12
Ответ Создать тему
Новые блоги и статьи
PhpStorm 2025.3: WSL Terminal всегда стартует в ~
and_y87 14.12.2025
PhpStorm 2025. 3: WSL Terminal всегда стартует в ~ (home), игнорируя директорию проекта Симптом: После обновления до PhpStorm 2025. 3 встроенный терминал WSL открывается в домашней директории. . .
Как объединить две одинаковые БД Access с разными данными
VikBal 11.12.2025
Помогите пожалуйста !! Как объединить 2 одинаковые БД Access с разными данными.
Новый ноутбук
volvo 07.12.2025
Всем привет. По скидке в "черную пятницу" взял себе новый ноутбук Lenovo ThinkBook 16 G7 на Амазоне: Ryzen 5 7533HS 64 Gb DDR5 1Tb NVMe 16" Full HD Display Win11 Pro
Музыка, написанная Искусственным Интеллектом
volvo 04.12.2025
Всем привет. Некоторое время назад меня заинтересовало, что уже умеет ИИ в плане написания музыки для песен, и, собственно, исполнения этих самых песен. Стихов у нас много, уже вышли 4 книги, еще 3. . .
От async/await к виртуальным потокам в Python
IndentationError 23.11.2025
Армин Ронахер поставил под сомнение async/ await. Создатель Flask заявляет: цветные функции - провал, виртуальные потоки - решение. Не threading-динозавры, а новое поколение лёгких потоков. Откат?. . .
Поиск "дружественных имён" СОМ портов
Argus19 22.11.2025
Поиск "дружественных имён" СОМ портов На странице: https:/ / norseev. ru/ 2018/ 01/ 04/ comportlist_windows/ нашёл схожую тему. Там приведён код на С++, который показывает только имена СОМ портов, типа,. . .
Сколько Государство потратило денег на меня, обеспечивая инсулином.
Programma_Boinc 20.11.2025
Сколько Государство потратило денег на меня, обеспечивая инсулином. Вот решила сделать интересный приблизительный подсчет, сколько государство потратило на меня денег на покупку инсулинов. . . .
Ломающие изменения в C#.NStar Alpha
Etyuhibosecyu 20.11.2025
Уже можно не только тестировать, но и пользоваться C#. NStar - писать оконные приложения, содержащие надписи, кнопки, текстовые поля и даже изображения, например, моя игра "Три в ряд" написана на этом. . .
Мысли в слух
kumehtar 18.11.2025
Кстати, совсем недавно имел разговор на тему медитаций с людьми. И обнаружил, что они вообще не понимают что такое медитация и зачем она нужна. Самые базовые вещи. Для них это - когда просто люди. . .
Создание Single Page Application на фреймах
krapotkin 16.11.2025
Статья исключительно для начинающих. Подходы оригинальностью не блещут. В век Веб все очень привыкли к дизайну Single-Page-Application . Быстренько разберем подход "на фреймах". Мы делаем одну. . .
КиберФорум - форум программистов, компьютерный форум, программирование
Powered by vBulletin
Copyright ©2000 - 2025, CyberForum.ru