名前空間
変種
操作

ソースファイルのインクルード

From cppreference.com

ディレクティブの直後の行で、現在のソースファイルに別のソースファイルをインクルードします。

目次

[編集] 構文

#include < h-char-sequence > new-line (1)
#include " q-char-sequence " new-line (2)
#include pp-tokens new-line (3)
__has_include ( " q-char-sequence " )
__has_include ( < h-char-sequence > )
(4) (C23以降)
__has_include ( string-literal )
__has_include ( < h-pp-tokens > )
(5) (C23以降)
1) h-char-sequence によって一意に識別されるヘッダーを検索し、ディレクティブをヘッダーの全内容に置き換えます。
2) q-char-sequence によって識別されるソースファイルを検索し、ディレクティブをソースファイルの全内容に置き換えます。(1)にフォールバックし、q-char-sequence をヘッダー識別子として扱うこともあります。
3) (1)(2) も一致しない場合、pp-tokens はマクロ置換を受けます。置換後のディレクティブは、再度 (1) または (2) とのマッチが試みられます。
4) ヘッダーまたはソースファイルがインクルード可能かどうかをチェックします。
5) (4) が一致しない場合、h-pp-tokens はマクロ置換を受けます。置換後のディレクティブは、再度 (4) とのマッチが試みられます。
new-line - 改行文字
h-char-sequence - 1つ以上の h-char のシーケンス。以下のいずれかが現れると未定義動作を引き起こします
  • 文字 '
  • 文字 "
  • 文字 \
  • 文字シーケンス //
  • 文字シーケンス /*
h-char - 改行と > を除くソース文字集合の任意のメンバ
q-char-sequence - 1つ以上の q-char のシーケンス。以下のいずれかが現れると未定義動作を引き起こします
  • 文字 '
  • 文字 \
  • 文字シーケンス //
  • 文字シーケンス /*
q-char - 改行と " を除くソース文字集合の任意のメンバ
pp-tokens - 1つ以上の前処理トークンのシーケンス
string-literal - 文字列リテラル
h-pp-tokens - > を除く1つ以上の前処理トークンのシーケンス

[編集] 説明

1) h-char-sequence で識別されるファイルを処理系定義の方法で検索します。この構文の意図は、処理系の管理下にあるファイルを検索することです。典型的な実装では、標準インクルードディレクトリのみを検索します。標準Cライブラリは、これらの標準インクルードディレクトリに暗黙的に含まれています。標準インクルードディレクトリは通常、ユーザーがコンパイラオプションを通じて制御できます。
2) q-char-sequence で識別されるファイルを処理系定義の方法で検索します。この構文の意図は、処理系の管理下にないファイルを検索することです。典型的な実装では、まず現在のファイルが存在するディレクトリを検索し、ファイルが見つからない場合にのみ、(1) と同様に標準インクルードディレクトリを検索します。
3) ディレクティブ内の include の後の前処理トークンは、通常のテキストと同様に処理されます(つまり、現在マクロ名として定義されている各識別子は、その置換リストの前処理トークンに置き換えられます)。すべての置換の後の結果のディレクティブは、前の2つの形式のいずれかに一致する必要があります。<> の前処理トークンペア、または一対の " 文字の間の前処理トークンのシーケンスを単一のヘッダー名前処理トークンに結合する方法は、処理系定義です。
4) h-char-sequence または q-char-sequence によって識別されるヘッダーまたはソースファイルは、その前処理トークンシーケンスが構文 (3)pp-tokens であったかのように検索されますが、それ以上のマクロ展開は行われません。もしそのようなディレクティブが #include ディレクティブの構文要件を満たさない場合、プログラムは不適格となります。__has_include 式は、ソースファイルの検索が成功した場合は 1 に、検索が失敗した場合は 0 に評価されます。
5) この形式は、構文 (4) が一致しない場合にのみ考慮され、その場合、前処理トークンは通常のテキストと同様に処理されます。

ファイルが見つからない場合、プログラムは不適格となります。

__has_include は、 #if および #elif の式の中で展開できます。 #ifdef, #ifndef, #elifdef, #elifndef, および defined によっては定義済みマクロとして扱われますが、それ以外の場所では使用できません。

(C23以降)

[編集] 注意

典型的な実装では、構文 (1) の場合、標準インクルードディレクトリのみを検索します。標準Cライブラリは、これらの標準インクルードディレクトリに暗黙的に含まれています。標準インクルードディレクトリは通常、ユーザーがコンパイラオプションを通じて制御できます。

構文 (2) の意図は、処理系の管理下にないファイルを検索することです。典型的な実装では、まず現在のファイルが存在するディレクトリを検索し、その後 (1) にフォールバックします。

ファイルがインクルードされると、それは翻訳フェーズ 1-4 によって処理されます。これには、ネストした #include ディレクティブの再帰的な展開が含まれる可能性があり、そのネストの深さは処理系定義の制限までです。同じファイルの繰り返しインクルードや、ファイルが(おそらく推移的に)自身をインクルードすることによる無限再帰を避けるために、ヘッダーガードが一般的に使用されます:ヘッダー全体を以下で囲みます。

#ifndef FOO_H_INCLUDED /* any name uniquely mapped to file name */
#define FOO_H_INCLUDED
// contents of the file are here
#endif

多くのコンパイラは、同様の効果を持つ非標準の pragma #pragma once も実装しています。これは、同じファイル(ファイルの同一性はOS固有の方法で決定されます)が既にインクルードされている場合に、そのファイルの処理を無効にします。

__has_include の結果が 1 であることは、指定された名前のヘッダーまたはソースファイルが存在することのみを意味します。そのヘッダーまたはソースファイルをインクルードしたときにエラーが発生しないことや、有用なものが含まれていることを意味するわけではありません。

[編集]

[編集] 参照

  • C23標準 (ISO/IEC 9899:2024)
  • 6.4.7 Header names (p: 69)
  • 6.10.1 Conditional inclusion (p: 165-169)
  • 6.10.2 Source file inclusion (p: 169-170)
  • C17標準 (ISO/IEC 9899:2018)
  • 6.10.2 Source file inclusion (p: 119-120)
  • C11標準 (ISO/IEC 9899:2011)
  • 6.10.2 Source file inclusion (p: 164-166)
  • C99標準 (ISO/IEC 9899:1999)
  • 6.10.2 Source file inclusion (p: 149-151)
  • C89/C90標準 (ISO/IEC 9899:1990)
  • 3.8.2 Source file inclusion

[編集] 関連項目

C標準ライブラリのヘッダーファイル一覧
C++ドキュメントソースファイルのインクルード
English 日本語 中文(简体) 中文(繁體)