web-dev-qa-db-ja.com

Windowsでディレクトリ区切り文字を取得しますか? ( '\'、 '/'など)

tl; dr:システムの現在のディレクトリ区切り文字をWindowsに問い合わせるにはどうすればよいですか?


Windowsのバージョンが異なれば動作も異なるようです(たとえば、\/はどちらも英語バージョンで動作します ¥は明らかに日本語バージョンで、₩は明らかに韓国語バージョンです 、など.。

これをハードコーディングすることを避け、代わりに実行時にWindowsに問い合わせる方法はありますか?

注意:

理想的には、ソリューションはnotのような高レベルのDLLに依存する必要がありますShlWAPI.dll、低レベルのライブラリもこれに依存しているため。したがって、実際にはkernel32.dllまたはntdll.dllなどに依存する必要があります...何かを見つけるのに問題がありますが、高レベルまたは低レベル。

編集:

少し実験したところ、順方向に変換するのはWin32サブシステム(つまり、kernel32.dll...またはRtlDosPathNameToNtPathName_Untdll.dllですか?わからない、テストしなかった...)であることがわかりました。カーネルではなく、スラッシュからバックスラッシュへ。 (接頭辞\\?\を使用すると、パスの後半でスラッシュを使用できなくなります。また、NTネイティブユーザーモードAPIもスラッシュで失敗します。)

つまり、Windowsに完全に「組み込まれている」わけではなく、単なる互換性機能です。つまり、パスの前にランダムに\\?\を付けるプログラムは自動的に中断されるため、バックスラッシュの代わりにスラッシュを盲目的に置き換えることはできません。スラッシュ。

私はこれに関してどのような結論を下すかについて複雑な気持ちを持っていますが、私はそれについて言及したいと思いました。

(パス区切り文字はディレクトリではなくパスの区切りに使用されるため、技術的には正しくありませんが、これを「パス区切り文字」としてタグ付けしました(; vs. \)うまくいけば、人々は私が意図したことを理解します。)

21
user541686

および¥文字は、それぞれの韓国および日本のWindowsバージョンでディレクトリ区切り記号として表示されますが、これらのバージョンのWindowsが同じUnicodeコードポイントU+005cを表す方法にすぎません。グリフ。バックスラッシュの基礎となるコードポイントは、英語のWindowsバージョンと日本語および韓国語のWindowsバージョンで同じです。

これに関する追加の確認は、このページにあります: http://msdn.Microsoft.com/en-us/library/dd374047(v = vs.85).aspx

ファイル名の文字セットのセキュリティに関する考慮事項

日本語システムで使用されるWindowsコードページとOEM文字セットには、円記号(¥)の代わりに円記号(\)が含まれています。したがって、円文字はNTFSおよびFATファイルシステムでは禁止されている文字です。 Unicodeを日本語コードページにマッピングする場合、変換関数は円記号(U + 005C)と通常のUnicode円記号(U + 00A5)の両方をこの同じ文字にマッピングします。セキュリティ上の理由から、アプリケーションでは通常、FATファイル名として使用するために変換される可能性のあるUnicode文字列の文字U + 00A5を許可しないでください。

また、システムのパス区切り文字を取得するWindows API関数については知りませんが、すべての状況で\であると信頼できます。

http://msdn.Microsoft.com/en-us/library/aa365247%28VS.85%29.aspx#naming_conventions

次の基本的なルールにより、アプリケーションは、ファイルシステムに関係なく、ファイルとディレクトリの有効な名前を作成および処理できます。

.。

バックスラッシュ(\)を使用して、パスのコンポーネントを区切ります。バックスラッシュは、ファイル名をそのパスへのパスから分割し、あるディレクトリ名をパス内の別のディレクトリ名から分割します。実際のファイルまたはディレクトリの名前に円記号を使用することはできません。これは、名前をコンポーネントに区切る予約文字であるためです。

.。

/について

Windowsは API関数のディレクトリ区切り文字として/ の使用をサポートする必要がありますが、必ずしもコマンドプロンプト(command.com)では必要ありません。

注WindowsAPIのファイルI/O関数は、名前をNTスタイルの名前に変換する一環として、「/」を「\」に変換します。ただし、次のセクションで説明する「\?」プレフィックスを使用する場合は除きます。

これらすべての真実を理解するのは「難しい」ですが、これはWindowsパスの/に関する非常に役立つリンクかもしれません: http://bytes.com/topic/python/answers/23123 -when-did-windows-start-accepting-forward-slash-path-separator

35
wkl

元の投稿者は、他の誰かの回答へのコメントに「カーネルモード」というフレーズを追加しました。

元の質問がカーネルモードについて尋ねることを意図していた場合、パス区切り文字である/に依存することはおそらく良い考えではありません。ファイルシステムが異なれば、ディスク上で異なる文字セットを使用できます。 Windowsのファイルシステムドライバーが異なれば、異なる文字セットを使用することもできます。通常、基になるファイルシステムがディスク上で受け入れない文字を含めることはできませんが、動作がおかしくなる場合があります。たとえば、Posixモードでは、NTFSは通常これらの文字を許可していませんが、コンポーネント名にNTFSパーティションのパス名にいくつかの文字を含めることができます。 (しかし、Posixでは明らかに/はそれらの1つではありません。)

Unicodeのカーネルモードでは、U + 005Cは常に円記号であり、常にパス区切り文字です。円とウォンのUnicodeコードポイントはU + 005Cではなく、パス区切り文字でもありません。

ANSIのカーネルモードでは、どのANSIコードページに応じて問題が発生します。 ASCIIに十分に類似しているコードページでは、0x5Cはバックスラッシュであり、パス区切り文字です。 ANSIコードページ932および949では、0x5Cは円記号ではありませんが、発生場所によっては0x5Cがパス区切り文字になる場合があります。 0x5Cがマルチバイト文字の最初のバイトである場合、それは円記号またはウォン記号であり、パス区切り文字です。 0x5Cがマルチバイト文字の2番目のバイトである場合、それ自体は文字ではないため、円記号やウォン記号ではなく、パス区切り文字でもありません。特定の文字が実際に文字全体であるかどうかを判断するには、文字列の先頭から解析を開始する必要があります。また、中国語とUTF-8では、マルチバイト文字は2文字より長くなる場合があります。

4

標準のスラッシュ(/)DOSとWindowsのすべてのバージョンで常に機能してきました。これを使用する場合、日本語版と韓国語版のWindowsで円記号がどのように表示されるかについて心配する必要はありません。また、POSIX(を含む)とは対照的に、Windowsのパス区切り文字を特殊なケースにする必要もありません。マック)。どこでもスラッシュを使用するだけです。