- ベストアンサー
相対パスでのインクルードパス指定の正体とは?
- Visual C++ 2017を使用したプロジェクト開発で、相対パスを使用してインクルードパスを指定する方法について説明します。
- プロジェクトファイルやソースファイルは開発用ディレクトリの直下にあり、その中にL2と同じ階層にあるincludeディレクトリが存在します。
- インクルードディレクトリの指定やソースファイルからの相対パスの解釈により、コンパイルが通る理由やエラーが発生する理由についても解説します。
- みんなの回答 (2)
- 専門家の回答
質問者が選んだベストアンサー
> インクルードパスに foo を追加すると、foo は相対パスをたどる時の基準点にもなると言うことでしょうか? そういうことです。 マイクロソフト(https://docs.microsoft.com/ja-jp/cpp/build/reference/i-additional-include-directories)によれば、 以下、引用 コンパイラは、次の順序でディレクトリを検索します。 1.ソース ファイルを含むディレクトリ。 2.指定されたディレクトリ、 /I CL で出現する順序でのオプションです。 3.指定したディレクトリ、 INCLUDE環境変数。 引用終わり とのことです。 コンパイラ(プリプロセッサ)からしてみれば、インクルード指令(#include)を読み込んだ時、上記の順番でディレクトリを検索し、ファイルが見つかればインクルード処理を行います。 この時、ファイル名が単なるファイル名だろうと、相対ファイル名だろうと同じです。 > そうすると、ある相対パスの表現が、別の階層にある複数の同名のディレクトリを指してしまうことになりませんか? それが何か問題なのですか? 相対パスでなくとも複数の同名ファイル名がインクルードパスに現れることはあり得ますが、上記の通りディレクトリの検索順序は決まっていますので、その順に検索を行い、先に見つかったものがインクルードされます。 ソースファイルを記述する者はその検索順序を意識してインクルード指令を記述する、またはディレクトリ構成を作成する必要があります。 > 意図したのは、fooの中にあるファイルを#includeの検索パスに含めて欲しいだけなのですが。 インクルードパスとはそういうものだからしょうがないでしょうね。 逆にそうなっていなかったら、階層構造を持つライブラリを使用する時、インクルードパスを複数書く必要があって面倒。例えば #include <sys/stat.h>
その他の回答 (1)
- maru_yoshi_
- ベストアンサー率39% (17/43)
MyProj以下のソースファイルから見て ../../../ はL2階層なので、 L4階層が余分なのではないかと思われます。 でL4階層が余分であるとして、、、 インクルードパスに foo を追加したので、プリプロセッサは foo から ../../にあるinclude/test.h を見つけることができ、 コンパイルは成功します。
お礼
ご回答ありがとうございます。 仰る通りL4が余分でした。失礼しました。 で、インクルードパスに foo を追加すると、foo は相対パスをたどる時の基準点にもなると言うことでしょうか? そうすると、ある相対パスの表現が、別の階層にある複数の同名のディレクトリを指してしまうことになりませんか? 意図したのは、fooの中にあるファイルを#includeの検索パスに含めて欲しいだけなのですが。
お礼
なるほど、MSのサイトにも説明がありましたね。 インクルードパスが増えると検索の基準点も増えてしまい、特に相対パス指定の場合は直感的にどのフォルダが検索対象になっているのか把握しづらいですね。