Заголовок C ++ и CPP включает - PullRequest
3 голосов
/ 17 января 2012

быстрый вопрос.

Я пытаюсь разобраться с C ++, и сегодня я провел часы с ошибкой компоновщика двойного определения («это уже было определено!»), И я наконец понял, что это потому, что у меня был макет как таковой:

  • main.cpp

    #include Dog.cpp
    
  • Dog.cpp

    #include Dog.h
    
  • Dog.h

    // (Dog class and prototype of test function)
    

А теперь, когда я это выяснил, включив Dog.h вместо Dog.cpp в main.cpp.

При включении файла .h файл .cpp с идентичным префиксом компилируется с программой?

Я был поражен, когда программа работала только с включенным .h и без ссылок на Dog.cpp. Я провел целую вечность, гугляя, но никакие ответы не помогли мне понять, что происходит.

Редактировать : Я забыл добавить, что я создал прототип в .h, и определил функцию для класса в .cpp, и это то, что дало мне «уже определенную» ошибку.

Ответы [ 4 ]

7 голосов
/ 17 января 2012

При включении файла .h файл .cpp с идентичным префиксом компилируется с программой?Я был поражен, когда программа работала только с включенным .h и без ссылок на Dog.cpp.

Нет.

Ваша программа построена поэтапно.

  • Для фазы компиляции необходимы только объявления в каждой единице перевода (примерно эквивалентно одному файлу .cpp с разрешением #include s).Причина, по которой объявления существуют даже в первую очередь, заключается в том, что это своего рода «обещание», что полное определение функции будет найдено позже.

    g++ -c Dog.cpp               # produces `Dog.o`
    g++ -c main.cpp              # produces `main.o`
    
  • Для связи фаза, символы разрешаются между единицами перевода.Вы должны связать воедино результат компиляции Dog.cpp и компиляции main.cpp (возможно, ваша IDE делает это для вас?), И этот процесс компоновки находит все правильные определения функций между ними, чтобы получить конечный исполняемый файл.

    g++ Dog.o main.o -o program  # produces executable `program`
    

    (Либо так, либо вы еще не дошли до фазы соединения, а просто имеете объектный файл (Dog.o); вы не можете выполнить его частично, потому что у него нетвсе определения функций указаны в.)

Две фазы могут быть выполнены одновременно, с помощью «стенографии»:

g++ Dog.cpp main.cpp -o program  # compiles, links and produces executable
0 голосов
/ 17 января 2012

Вы не указываете, как вы его компилируете. Если вы используете IDE и автоматически добавили в проект новые .h и .cpp, то все они будут автоматически скомпилированы и связаны.

Существует два этапа создания исполняемого файла: компиляция и компоновка. Компиляция - это когда код интерпретируется и переводится в код более низкого уровня. Связывание - это то, где все функции, которые вы использовали, решаются. Здесь вы получили ошибку дублирующейся функции.

0 голосов
/ 17 января 2012

Нет, файл .cpp НЕ автоматически компилируется. Вы можете сделать это вручную, создать make-файл или использовать IDE, в которой оба они находятся в одном проекте.

0 голосов
/ 17 января 2012

Включение не приводит к автоматической компиляции, нет.

Фактически, фактический компилятор вообще не видит оператор #include.Он был удален на более раннем этапе (называемом препроцессором).

Я не уверен, как он мог бы скомпилироваться, если вы никогда не скомпилировали файл Dog.cpp.Вы ссылались на какие-либо объекты с кодом, определенным в этом файле?

...