いろいろ備忘録日記

主に .NET とか Go とか Flutter とか Python絡みのメモを公開しています。

Pythonメモ-11 (ディレクトリの削除, os.remove, os.rmdir, os.removedirs, shutil.rmtree)

概要

未だにちょこちょこ忘れてて、同じ間違いをするので忘れないようにメモ。

Pythonでディレクトリを削除しようとしてて、いつもの調子で

os.remove('/tmp/a')

とかするとOSErrorが発生します。Windowsだと以下のような感じ。

PermissionError: [WinError 5] アクセスが拒否されました。: '/tmp/a'

で、毎回「ん?パーミッション??なんで??」ってなるのですが、実際は

os.remove でディレクトリは削除できない。

って事なんですね。ドキュメントにも書いてあります。

16.1. os — 雑多なオペレーティングシステムインタフェース — Python 3.6.1 ドキュメント

ファイル path を削除します。 path がディレクトリの場合、OSError が送出されます; ディレクトリの削除には rmdir() を使用してください。

アクセス拒否ってエラーメッセージより、ディレクトリは対応してないから rmdir 使ってねってエラーメッセージの方が個人的には嬉しいな。

てことで、os.rmdir() を使うぜってなって動かすと、ディレクトリが空の場合はおけ。空じゃない場合は

OSError: [WinError 145] ディレクトリが空ではありません。: '/tmp/a'

って出ます。( ;∀;) メンドクセーナー

中身を消してから、rmdir呼べばいいのですが、面倒なときは以下が便利です。

shutil.rmtree('/tmp/a')

こっちは、コンテンツがあっても消してくれます。注意点として再帰で削除されるので

単独のディレクトリのみ消したい場合は、ちゃんと末端のディレクトリを指定するようにしないと駄目です。

サンプル

以下、サンプルです。

os.mkdir('/tmp/test01')
try:
    # os.remove ではディレクトリは削除できない
    # 中身が空でもダメ
    os.remove('/tmp/test01')
except OSError as e:
    pr('os.remove', e)

# 中身が空の場合は、rmdir() で削除できる
os.rmdir('/tmp/test01')

# サブディレクトリも含めて一気に作成
os.makedirs('/tmp/a/b/c/d')

# サブディレクトリも含めて一気に削除
# ただし、中身が空の場合のみ
os.removedirs('/tmp/a/b/c/d')

# ディレクトリ内にコンテンツがあると removedirs() は失敗する
os.makedirs('/tmp/a/b/c')
print('hello world', file=open('/tmp/a/b/c/test.txt', mode='wt'))
try:
    os.removedirs('/tmp/a/b/c')
except OSError as e:
    pr('os.removedirs', e)

# shutil.rmtree() はコンテンツがあっても再帰削除してくれる
shutil.rmtree('/tmp/a')

ソースコードは以下でも見れます。

try-python/rmdir01.py at master · devlights/try-python · GitHub

参考情報

stackoverflow.com

16.1. os — 雑多なオペレーティングシステムインタフェース — Python 3.6.1 ドキュメント

11.10. shutil — 高水準のファイル操作 — Python 3.6.1 ドキュメント


過去の記事については、以下のページからご参照下さい。

サンプルコードは、以下の場所で公開しています。