Unixパス文字列を操作するためのライブラリを書いています。そういうわけで、私はほとんどの人が気にしないであろう構文のいくつかのあいまいなコーナーを理解する必要があります。
たとえば、私が知る限り、foo/bar
およびfoo//bar
両方が同じ場所を指しています。
また、~
は通常、ユーザーのホームディレクトリを表しますが、パスのmiddleにある場合はどうなりますか?次に何が起こりますか?
考えられるすべてのケースを正しく処理するコードを記述しようとする場合、これらと他の数十のあいまいな質問に答える必要があります。 exactの構文規則を説明する明確なリファレンスを知っている人はいますか?
(残念ながら、「Unixパス構文」などの用語を検索すると、$PATH
変数...一体、この質問に適したタグを見つけるのに苦労しています!)
パスには3つのタイプがあります。
foo
、foo/bar
、../a
、.
などの相対パス。それらは/
で始まっておらず、そのパスを使用してシステムコールを行うプロセスの現在のディレクトリを基準にしています。/
、/foo/bar
、///x
などの絶対パス。それらは、1つまたは3つ以上の/
で始まり、相対的ではなく、/
ルートディレクトリから検索されます。//foo
を特別に扱うことができますが、その方法は指定されていません。 一部のシステムでは、ネットワークファイルなどの特殊なケースでこれを使用します 。スラッシュは2つでなければなりません。開始時を除いて、スラッシュのシーケンスは1つのように機能します。
~
はシェルにのみ特別です 、シェルによって拡張され、システムに特別ではありません。展開方法はシェルに依存します。シェルは、グロビング(*.txt
)や変数展開/$foo/$bar
などのような他の形式の展開を行います。システムに関する限り、~foo
は_foo
またはfoo
のような単なる相対パスです。
心に留めておくべきこと:
foo/
はfoo
と同じではありません。ほとんどのシステムのほとんどのシステムコールでは、foo
よりもfoo/.
に近いです(特にfoo
がシンボリックリンクの場合)(ただし、foo//
はfoo/
と同じです)。a/b/../c
は、必ずしもa/c
と同じであるとは限りません(たとえば、a/b
がシンボリックリンクの場合)。 ..
を特別に扱わないことが最善です。a/././././b
をa/b
と同じと見なしても安全です。たとえば、私が知る限り、foo/barとfoo // barはどちらも同じ場所を指しているようです。
はい。これはよくあることです。ソフトウェアは、最初の部分がスラッシュで終了していないと想定してパスを連結する場合があるため、確認のために1つスローされます(つまり、2つ以上になる場合があります)。 foo///bar
およびfoo/////bar
もfoo/bar
と同じ場所を指します。パス操作ライブラリのニース関数は、任意の数の連続するスラッシュを1に減らすものです(パスの先頭で、URLのような方法で使用できる場合や、Stephaneが指摘するように、不特定の特別な目的)。
また、通常〜はユーザーのホームディレクトリを表します
その変換は、シェルと tilde exapansion を介して行われます。これは、パスの最初の文字である場合にのみ機能します。これに対処する必要があるかどうかは、状況によって異なります。ライブラリが、たとえばパスを含むコマンドライン引数を受け取る通常のプログラムで使用される場合、パスを見ると、チルダ展開はすでに完了しています 。テキストファイルから直接パスを処理している場合、それが問題であると私が見ることができる唯一の状況です。
それ以外の場合、~
は* nixパスの正当な文字であり、他のものに変更しないでください。 per this のように、UNIXファイル名で無効な文字は/
(パス区切り文字であるため)と "null"(別名:ゼロバイト)のみです。テキストでは一般的に違法です。