В чем разница между использованием угловых скобок и использованием кавычек в include
выражении в языках программирования C и C ++ , как показано ниже?
#include <filename>
#include "filename"
c++
c
include
header-files
c-preprocessor
quest49
источник
источник
Ответы:
На практике разница заключается в том, где препроцессор ищет включенный файл.
Для
#include <filename>
поиска препроцессора в зависимости от реализации, обычно в каталогах поиска, предварительно назначенных компилятором / IDE. Этот метод обычно используется для включения стандартных заголовочных файлов библиотеки.Для
#include "filename"
препроцессор поисков первых в том же каталоге, что и файл , содержащий директиву, а затем следует по пути поиска , используемый для#include <filename>
формы. Этот метод обычно используется для включения файлов заголовков, определенных программистом.Более полное описание доступно в документации GCC по путям поиска .
источник
#include <...>
использовал пакет, установленный в системе, и#include "..."
версию соседнего репозитория. Я мог бы иметь это задом наперед. В любом случае, защита включения в упакованном заголовке имеет префикс подчеркивания. (Это может быть соглашение о пакетах или способ преднамеренно предотвратить смешивание двух, хотя для меня было бы лучше иметь смысл классификаторы версий.)Единственный способ узнать это - прочитать документацию вашей реализации.
В стандарте C , раздел 6.10.2, пункты 2–4 говорится:
источник
Последовательность символов между <и> однозначно относится к заголовку, который не обязательно является файлом. Реализации могут свободно использовать последовательность символов по своему желанию. (В основном, однако, просто обработайте его как имя файла и выполните поиск по пути включения , как указано в других сообщениях.)
Если
#include "file"
форма используется, реализация сначала ищет файл с заданным именем, если это поддерживается. Если нет (поддерживается) или если поиск не удался, реализация ведет себя так, как если бы использовалась другая#include <file>
форма ( ).Кроме того, существует третья форма, которая используется, когда
#include
директива не соответствует ни одной из форм выше. В этой форме некоторая базовая предварительная обработка (например, расширение макроса) выполняется над «операндами»#include
директивы, и ожидается, что результат будет соответствовать одной из двух других форм.источник
<
и>
в качестве ключа для индексации в библиотеке.Некоторые хорошие ответы здесь ссылаются на стандарт C, но забыли стандарт POSIX, особенно специфическое поведение команды c99 (например, C compiler) .
В соответствии с открытой базой спецификаций Group Issue 7 ,
Таким образом, в POSIX-совместимой среде с POSIX-совместимым компилятором C,
#include "file.h"
скорее всего,./file.h
сначала будет искать , где.
находится каталог, где находится файл с#include
оператором, в то время как#include <file.h>
, скорее всего,/usr/include/file.h
сначала будет искать , где/usr/include
определена ваша система. обычные места для заголовков (кажется, это не определено POSIX).источник
c99
- которая является именем POSIX для компилятора C. (Стандарт POSIX 2008 едва ли мог ссылаться на C11; обновление 2013 года для POSIX 2008 не изменило стандарт C, на который он ссылался.)-L
.Документация GCC говорит следующее о разнице между ними:
источник
Оно делает:
с
.
каталогом файла, в котором#include
он содержится, и / или текущим рабочим каталогом компилятора, и / илиdefault_include_paths
а также
Если
./
есть<default_include_paths>
, то это не имеет значения.Если
mypath/myfile
находится в другом каталоге include, поведение не определено.источник
#include "mypath/myfile"
не является эквивалентом#include "./mypath/myfile"
. Как говорится в ответе piCookie, двойные кавычки сообщают компилятору о поиске в соответствии с реализацией, что включает в себя поиск в указанных местах#include <...>
. (На самом деле, это, вероятно, эквивалентно, но только потому, что, например, его/usr/include/mypath/myfile
можно назвать/usr/include/./mypath/myfile
- по крайней мере, в Unix-подобных системах.)defaultincludepaths
, а не дает другое значение.
(как указано выше). Это имеет ожидаемое последствие, что оба#include "..."
и#include <...>
ищут в dirpath<file>
Включает говорит препроцессор для поиска в-I
каталогах и в предопределенных каталогах первых , то в директории .c файла."file"
Включает говорит препроцессор для поиска каталога исходного файла первого , а затем вернуться к-I
и предопределено. Все пункты назначения в любом случае ищутся, только порядок поиска отличается.Стандарт 2011 главным образом обсуждает включаемые файлы в «16.2 Включение исходного файла».
Обратите внимание, что
"xxx"
форма ухудшается до<xxx>
формы, если файл не найден. Остальное определяется реализацией.источник
-I
бизнес указан?-I
.#include <file.h>
сообщает компилятору о поиске заголовка в каталоге «file.h
include », например, для MinGW, который компилятор будет искать в C: \ MinGW \ include \ или там, где установлен ваш компилятор.#include "file"
говорит компилятору искать текущий каталог (то есть каталог, в котором находится исходный файл)file
.Вы можете использовать
-I
флаг для GCC, чтобы сказать ему, что, когда он встречает включение с угловыми скобками, он должен также искать заголовки в каталоге после-I
. GCC будет обрабатывать каталог после флага, как если бы он былincludes
каталогом.Например, если у вас есть файл, который вызывается
myheader.h
в вашем собственном каталоге, вы можете сказать#include <myheader.h>
, вызвали ли вы GCC с флагом-I .
(указывающим, что он должен искать включения в текущем каталоге.)Без
-I
флажка вам придется использовать,#include "myheader.h"
чтобы включить файл, или перейтиmyheader.h
вinclude
каталог вашего компилятора.источник
По стандарту - да, они разные
Обратите внимание, что в стандарте не говорится о какой-либо связи между способами, определяемыми реализацией. Первая форма ищет одним способом, определяемым реализацией, а другой - способом (возможно, другим), определяемым реализацией. Стандарт также указывает, что должны присутствовать определенные включаемые файлы (например,
<stdio.h>
).Формально вам нужно прочитать руководство для вашего компилятора, однако обычно (по традиции)
#include "..."
форма ищет каталог файла, в котором#include
был найден файл , а затем каталоги, которые#include <...>
ищет форма (путь включения, например, системные заголовки). ).источник
Спасибо за отличные ответы, особенно Адам Стельмащик, ПиКуки и Аиб.
Как и многие программисты, я использовал неофициальное соглашение об использовании
"myApp.hpp"
формы для файлов приложения и<libHeader.hpp>
формы для файлов библиотеки и системы компилятора, то есть файлов, указанных в/I
иINCLUDE
переменную среды, в течение многих лет , думая , что был стандарт.Однако стандарт C утверждает, что порядок поиска зависит от конкретной реализации, что может усложнить переносимость. Что еще хуже, мы используем jam, который автоматически определяет местонахождение включаемых файлов. Вы можете использовать относительные или абсолютные пути для ваших включаемых файлов. т.е.
Более старые версии MSVS требовали двойной обратной косой черты (\\), но теперь это не требуется. Я не знаю, когда это изменилось. Просто используйте косую черту для совместимости с 'nix (Windows примет это).
Если вы действительно беспокоитесь об этом, используйте
"./myHeader.h"
для включаемого файла в том же каталоге, что и исходный код (мой текущий, очень большой проект имеет несколько дублирующих имен включаемых файлов, разбросанных по всему - действительно проблема управления конфигурацией).Вот пояснение MSDN, скопированное сюда для вашего удобства).
источник
По крайней мере для версии GCC <= 3.0 форма угловых скобок не создает зависимости между включенным файлом и включающим файлом.
Поэтому, если вы хотите сгенерировать правила зависимости (используя опцию GCC -M для примера), вы должны использовать форму в кавычках для файлов, которые должны быть включены в дерево зависимостей.
(См. Http://gcc.gnu.org/onlinedocs/cpp/Invocation.html ).
источник
Для
#include ""
компилятора обычно выполняется поиск в папке файла, в которой содержатся включаемые, а затем и другие папки. Ибо#include <>
компилятор не ищет папку текущего файла.источник
<filename>
и другое и"filename"
ищет места, определенные реализацией.Когда вы используете #include <filename>, препроцессор ищет файл в каталоге заголовочных файлов C \ C ++ (stdio.h \ cstdio, string, vector и т. Д.). Но, когда вы используете #include «filename»: сначала препроцессор ищет файл в текущем каталоге, а если его нет - ищет его в каталоге заголовочных файлов C \ C ++.
источник
#include
директива обычная, она вообще не связана с файлами.#Include с угловыми скобками будет искать «список мест, зависящий от реализации» (что очень сложно сказать «системные заголовки») для файла, который будет включен.
#Include с кавычками будет просто искать файл (и, "в зависимости от реализации", bleh). Это означает, что в обычном английском языке он будет пытаться применить путь / имя файла, который вы выбрасываете в нем, и не будет предварять системный путь или вмешиваться в него в противном случае.
Кроме того, если #include "" завершается неудачно, стандарт перечитывается как #include <>.
В документации по gcc есть (специфичное для компилятора) описание, которое, хотя и относится к gcc, а не к стандарту, намного проще для понимания, чем разговоры о стандартах ISO в стиле юриста.
источник
zlib.h
в моих путях поиска «пользователя», и в пути поиска системы существует другая версия, тогда#include <zlib.h>
включает ли версию системы и#include "zlib.h"
мою собственную?Пример:
Имя файла здесь
Seller.h
:В реализации класса (например,
Seller.cpp
и в других файлах, которые будут использовать файлSeller.h
) теперь должен быть включен заголовок, определенный пользователем, следующим образом:источник
#include <>
для предопределенных заголовочных файловЕсли файл заголовка предопределен, вы просто пишете имя файла заголовка в угловых скобках, и это будет выглядеть так (при условии, что у нас есть предопределенное имя файла заголовка iostream):
#include " "
для заголовочных файлов программист определяетЕсли вы (программист) написали свой собственный файл заголовка, вы бы написали имя файла заголовка в кавычках. Итак, предположим, что вы написали заголовочный файл с именем
myfile.h
, тогда это пример того, как вы будете использовать директиву include для включения этого файла:источник
Многие из ответов здесь сосредоточены на путях, которые компилятор будет искать, чтобы найти файл. Хотя это то, что делает большинство компиляторов, соответствующий компилятор может быть предварительно запрограммирован с эффектами стандартных заголовков и обрабатываться, скажем,
#include <list>
как переключатель, и он вообще не должен существовать как файл.Это не чисто гипотетически. Есть по крайней мере один компилятор, который работает таким образом.
#include <xxx>
Рекомендуется использовать только со стандартными заголовками.источник
используется для включения стандартных библиотечных файлов. Таким образом, компилятор проверит места, где находятся стандартные заголовки библиотеки.
скажет компилятору включить определенные пользователем заголовочные файлы. Таким образом, компилятор проверит наличие этих заголовочных файлов в текущей папке или
-I
определенных папках.источник
В C ++ включить файл можно двумя способами:
Первый - #include, который указывает препроцессору искать файл в предопределенном местоположении по умолчанию. Это местоположение часто является переменной среды INCLUDE, которая обозначает путь для включения файлов.
И второй тип - #include «filename», который указывает препроцессору сначала искать файл в текущем каталоге, а затем искать его в предопределенных местоположениях, установленных пользователем.
источник
Форма 1 - #include <xxx>
Сначала ищет наличие заголовочного файла в текущем каталоге, откуда вызывается директива. Если не найден, выполняется поиск в предварительно сконфигурированном списке стандартных системных каталогов.
Форма 2 - #include "ххх"
Это ищет наличие заголовочного файла в текущем каталоге, откуда вызывается директива.
Точный список каталогов поиска зависит от целевой системы, способа настройки GCC и места его установки. Вы можете найти список каталогов поиска вашего компилятора GCC, запустив его с опцией -v.
Вы можете добавить дополнительные каталоги в путь поиска, используя - I dir , который заставляет искать dir после текущего каталога (для формы директивы в кавычках) и перед стандартными системными каталогами.
По сути, форма «xxx» - это не что иное, как поиск в текущем каталоге; если не найдено, возвращаясь к форме
источник
#include "header.h"
формы не точное, @personal_cloud. Я считаю ответ piCookie и Yann Droneaud наиболее актуальным, поскольку они определяют, откуда поступает их информация. Я не считаю, что голосование с наивысшим рейтингом также является полностью удовлетворительным.#include <filename>
Используется , когда файловая система в настоящее время упоминается. Это заголовочный файл, который можно найти в системных местах по умолчанию, таких как/usr/include
или/usr/local/include
. Для ваших собственных файлов, которые должны быть включены в другую программу, вы должны использовать#include "filename"
синтаксис.источник
В идеале вы должны использовать <...> для стандартных библиотек C и «...» для библиотек, которые вы пишете и присутствуют в текущем каталоге.
источник
Простое общее правило заключается в использовании угловых скобок для включения заголовочных файлов, которые поставляются с компилятором. Используйте двойные кавычки, чтобы включить любые другие файлы заголовков. Большинство компиляторов делают это так.
1.9 - Заголовочные файлы объясняют более подробно о директивах препроцессора. Если вы начинающий программист, эта страница должна помочь вам понять все это. Я узнал об этом здесь, и я следил за этим на работе.
источник
#include <filename>
используется, когда вы хотите использовать заголовочный файл системы C / C ++ или библиотеки компилятора. Этими библиотеками могут быть stdio.h, string.h, math.h и т. Д.
#include "path-to-file/filename"
используется, когда вы хотите использовать свой собственный файл заголовка, который находится в папке вашего проекта или где-то еще.
Для получения дополнительной информации о препроцессорах и заголовке. Читай С - Препроцессоры .
источник
#include <filename>
#include "filename"
#include <filename>
и ищет этот заголовочный файл, где хранятся системные заголовочные файлы.#include <filename>
.источник
Чтобы увидеть порядок поиска в вашей системе с помощью gcc, основываясь на текущей конфигурации, вы можете выполнить следующую команду. Вы можете найти более подробную информацию об этой команде здесь
cpp -v /dev/null -o /dev/null
источник
Включает файл, в котором каталог по умолчанию включен.
Включает файл в текущем каталоге, в котором он был скомпилирован.
источник
Существует два способа написать заявление #include. Это:
Смысл каждой формы
Эта команда будет искать файл
mylib.h
в текущем каталоге, а также указанный список каталогов, как упомянуто во включенном пути поиска, который мог быть установлен.Эта команда будет искать файл только
mylib.h
в указанном списке каталогов.Путь поиска для включения - это не что иное, как список каталогов, в которых будет выполняться поиск включаемого файла. Разные компиляторы C позволяют задавать путь поиска по-разному.
источник