1. ホーム
  2. python

[解決済み] os/path 形式に関係なく、パスからファイル名を抽出します。

2022-03-16 23:51:16

質問

オペレーティングシステムやパスの形式に関係なく、パスからファイル名を抽出するためにどの Python ライブラリを使用できますか?

例えば、以下のようなパスをすべて返したい。 c :

a/b/c/
a/b/c
\a\b\c
\a\b\c\
a\b\c
a/b/../../a/b/c/
a/b/../../a/b/c

解決方法は?

使用方法 os.path.split または os.path.basename Linuxでスクリプトを実行している場合、古典的なWindowsスタイルのパスを処理しようとすると、失敗します。

Windowsのパスでは、パスの区切り文字としてバックスラッシュとフォワードスラッシュのどちらかを使用することができます。そのため ntpath モジュール(Windowsで実行する場合はos.pathと等価)は、すべての (1) のパスを、すべてのプラットフォームで使用することができます。

import ntpath
ntpath.basename("a/b/c")

もちろん、ファイルの末尾がスラッシュであれば、ベースネームは空になるので、自分で関数を作って対処してください。

def path_leaf(path):
    head, tail = ntpath.split(path)
    return tail or ntpath.basename(head)

検証を行います。

>>> paths = ['a/b/c/', 'a/b/c', '\\a\\b\\c', '\\a\\b\\c\\', 'a\\b\\c', 
...     'a/b/../../a/b/c/', 'a/b/../../a/b/c']
>>> [path_leaf(path) for path in paths]
['c', 'c', 'c', 'c', 'c', 'c', 'c']


(1) 一つだけ注意点がある:Linuxのファイル名 はバックスラッシュを含むことがあります。 . だから、リナックスでは r'a/b\c' は常にファイル b\c の中で a フォルダを参照しますが、Windows では、常に c ファイルを b のサブフォルダを作成します。 a フォルダーに格納されます。そのため、パス内でフォワードスラッシュとバックスラッシュの両方が使用されている場合、次のようになります。 必要 を正しく解釈するためには、関連するプラットフォームを知っておく必要があります。実際には、バックスラッシュはLinuxのファイル名ではほとんど使われないので、Windowsのパスだと仮定するのが安全ですが、コーディングする際にはこのことを念頭に置いて、誤ってセキュリティホールを作らないようにしましょう。