フォルダの内容を削除するにはどうすればよいですか?


470

Pythonでローカルフォルダーの内容を削除するにはどうすればよいですか?

現在のプロジェクトはWindows用ですが、* nixもご覧ください。


2
* nixが正直であるために、私はただ使用するos.system('rm -rf folder')
Tilak Maddy

回答:


444
import os, shutil
folder = '/path/to/folder'
for filename in os.listdir(folder):
    file_path = os.path.join(folder, filename)
    try:
        if os.path.isfile(file_path) or os.path.islink(file_path):
            os.unlink(file_path)
        elif os.path.isdir(file_path):
            shutil.rmtree(file_path)
    except Exception as e:
        print('Failed to delete %s. Reason: %s' % (file_path, e))

4
非常に大きなディレクトリ、特にWindowsのネットワークディレクトリで作業していて、このプログラムが実行される環境を制御できる場合は、代わりにPy3.5の「os.scandir(folder)」関数を使用する価値があるかもしれませんlistdir。構文はその後かなり異なりますが、実装は非常に簡単です。他の人が望むならそれを投稿して幸せです。
Michael Scott Cuthbert

私はexcept Exception as e:それを読んでパイリント警告を受けていますW0703: Catching too general exception Exception。キャッチするより具体的な例外はありますか、それとも無視すべきですか?
John Hany 2017年

7
@ JohnHany、OSErrorをキャッチしたいと思います。
MikeB

246

あなたは単にこれを行うことができます:

import os
import glob

files = glob.glob('/YOUR/PATH/*')
for f in files:
    os.remove(f)

もちろん、パス内の他のフィルターを使用することもできます。たとえば、/ YOU / PATH / *。txtを使用して、ディレクトリ内のすべてのテキストファイルを削除します。


12
@Blueicefield *は隠しファイルを一覧表示しないため、追加する必要がありますglob.glob('path/.*)
satoru

5
ファイルのリストを削除するものの、何をする私には単純なようだ:import sh; sh.rm(files)
ロビン・ウィンズロウ

2
一方でimport sh; sh.rm(files)ルックきれいのないディレクトリ内の1024個の以上のファイルがある場合、あなたはトラブルに実行します。
ユージーン

235

以下を使用して、フォルダ自体とそのすべての内容を削除できますshutil.rmtree

import shutil
shutil.rmtree('/path/to/folder')
shutil.rmtree(path, ignore_errors=False, onerror=None)


ディレクトリツリー全体を削除します。pathはディレクトリを指す必要があります(ただし、ディレクトリへのシンボリックリンクは指しません)。場合IGNORE_ERRORSが真である、削除に失敗したことによるエラーは無視されます。falseまたは省略されている場合、そのようなエラーはonerrorで指定されたハンドラーを呼び出すことによって処理されます。省略されている場合は、例外が発生します。


270
これにより、コンテンツだけでなくフォルダ自体も削除されます。私はそれが質問がするものではないと思います。
Iker Jimenez、

3
いい答えだと思います。中身とフォルダを削除して、フォルダを作り直してみませんか?
cssndrx 2011

42
新しいディレクトリと古いディレクトリは同じではないからです。したがって、プログラムがディレクトリに座って物事を待っている場合、その下から敷物が引き出されます。
Mike Cooper

30
後にディレクトリを再作成してくださいrmtree。のようなものos.makedirs(dir)
Iulius Curt

3
ノー@IuliusCurt、私はディレクトリが、私は空にする必要があるラムに取り付けられていて、残念ながら私はそれを再作成し、削除することはできません:OSError: [Errno 16] Device or resource busy
アルノーP

80

mhawkeの答えを拡張すると、これが私が実装したものです。フォルダーのコンテンツはすべて削除されますが、フォルダー自体は削除されません。ファイル、フォルダ、シンボリックリンクを使用してLinuxでテストすると、Windowsでも動作するはずです。

import os
import shutil

for root, dirs, files in os.walk('/path/to/folder'):
    for f in files:
        os.unlink(os.path.join(root, f))
    for d in dirs:
        shutil.rmtree(os.path.join(root, d))

1
フォルダの内容を一覧表示するだけでなく、なぜ「ウォーク」するのですか?
Don

2
これは、ディレクトリも削除したい場合の正解です。 walkdirsとファイルを分割するために使用されます。ファイルは異なる方法で処理する必要があります。を使用することもできますがos.listdir、各エントリがディレクトリまたはファイルであるかどうかを手動で確認する必要があります。
dkamins 2012年

7
これは近いですが、os.walkとshutil.rmtreeはどちらも再帰的です。クリーニングする必要があるのは、ディレクトリ内の最上位にあるファイルとディレクトリだけなので、os.walkは不要です。os.listdirの要素にifステートメントを使用するだけで、それぞれがファイルかディレクトリかを確認できます。次に、それぞれremove / unlinkとrmtreeを使用します。
マシューアルパート2014年

1
@MatthewAlpertただし、os.walkここでは再帰しないことに注意してください。ジェネレータを返すのは、サブディレクトリを進めようとしたときに再帰的に調べられるだけであり、このループの最初の反復が完了するまでに、サブディレクトリはないためです。見て左。本質的にos.walkは、ここでは、最上位のフォルダーと最上位のファイルを区別する別の方法として使用されています。再帰は使用されておらず、そのためのパフォーマンスコストは発生しません。しかし、それは偏心的であり、あなたが提案するアプローチは、それがより明確で読みやすいので、単に優れていることに同意します。
Mark Amery

47

rmtreeフォルダを使用して再作成することは可能ですが、ネットワークドライブ上のフォルダを削除してすぐに再作成するときにエラーが発生しました。

ウォークを使用して提案されたソリューションはrmtree、フォルダーの削除に使用されるため機能せずos.unlink、以前はそれらのフォルダーにあったファイルを使用しようとする場合があります。これによりエラーが発生します。

投稿されたglobソリューションは、空ではないフォルダも削除しようとするため、エラーが発生します。

私はあなたが使うことを勧めます:

folder_path = '/path/to/folder'
for file_object in os.listdir(folder_path):
    file_object_path = os.path.join(folder_path, file_object)
    if os.path.isfile(file_object_path) or os.path.islink(file_object_path):
        os.unlink(file_object_path)
    else:
        shutil.rmtree(file_object_path)

1
他のディレクトリへのシンボリックリンクがある場合も、ソリューションでエラーが発生します。
Blueicefield 2013

@Blueicefield-例を提供できますか。Linuxでシンボリックリンクされたファイルとフォルダーを使用してテストしましたが、まだエラーを発生させることはできません。
jgoeders 14年

@jgoeders-ディレクトリへのシンボリックリンクがある場合os.path.isfile()False(シンボリックリンクをたどっているため)が返さshutil.rmtree()れ、最終的にはを発生させるシンボリックリンクが呼び出されますOSError("Cannot call rmtree on a symbolic link")
Rockallite 14

1
@Rockalliteはチェックによってislinkに修正されました
kevinf

1
また、@ kevinfはislink、ディレクトリへのシンボリックリンクを正しく処理するために、ここでのチェックの必要性を指摘するのに適切です。承認された回答にそのようなチェックを追加しました。
Mark Amery

20

この:

  • すべてのシンボリックリンクを削除します
    • デッドリンク
    • ディレクトリへのリンク
    • ファイルへのリンク
  • サブディレクトリを削除します
  • 親ディレクトリを削除しません

コード:

for filename in os.listdir(dirpath):
    filepath = os.path.join(dirpath, filename)
    try:
        shutil.rmtree(filepath)
    except OSError:
        os.remove(filepath)

他の多くの回答と同様に、これはファイル/ディレクトリの削除を可能にするために権限を調整しようとするものではありません。


15

ワンライナーとして:

import os

# Python 2.7
map( os.unlink, (os.path.join( mydir,f) for f in os.listdir(mydir)) )

# Python 3+
list( map( os.unlink, (os.path.join( mydir,f) for f in os.listdir(mydir)) ) )

ファイルとディレクトリも考慮したより堅牢なソリューションは(2.7)です。

def rm(f):
    if os.path.isdir(f): return os.rmdir(f)
    if os.path.isfile(f): return os.unlink(f)
    raise TypeError, 'must be either file or directory'

map( rm, (os.path.join( mydir,f) for f in os.listdir(mydir)) )

1
ジェネレーターを使用する大規模な操作の場合、部分的に効率がmap( os.unlink, (os.path.join( mydir,f) for f in os.listdir(mydir)) )
上がる

実際にこれを使用しようとすると、マップオブジェクトを反復処理する必要があるため、次のようにリストへの呼び出し(または反復処理が必要)が必要になりますlist(map(os.unlink, (os.path.join( mydir,f) for f in os.listdir(mydir))))
user25064

1つ目は答えに含まれていますが、2つ目は私には意味がありません。なぜイテラブルにマップされた関数を反復する必要があるのですか?マップはそれを行います。
fmonegaglia

1
Python3では、 実際に反復するためにラップmapインlistする必要があります。参照http://stackoverflow.com/questions/1303347/getting-a-map-to-return-a-list-in-python-3-xを
paulwasit

リンク解除はファイルに対してのみ機能するため、「mydir」に少なくとも1つのフォルダが含まれている場合、これは確実に機能しません...
kupsef

14

注:誰かが私の回答に反対票を投じた場合、私はここで説明することができます。

  1. 誰もが短い「n」の単純な答えが好きです。しかし、現実はそれほど単純ではない場合があります。
  2. 私の答えに戻ります。shutil.rmtree()ディレクトリツリーの削除に使用できることは知っています。私は自分のプロジェクトで何度も使用しました。ただし、ディレクトリ自体もによって削除されるshutil.rmtree()ことを理解する必要があります。これは一部には受け入れられるかもしれませんが、(副作用なしで)フォルダの内容削除する有効な回答ではありません。
  3. 副作用の例を紹介します。多数のコンテンツが存在する、カスタマイズされた所有者とモードビットを含むディレクトリがあるとします。次に、でそれを削除し、shutil.rmtree()で再構築しos.mkdir()ます。そして、代わりにデフォルトの(継承された)所有者とモードビットを持つ空のディレクトリを取得します。コンテンツやディレクトリを削除する権限がある場合でも、ディレクトリの元の所有者とモードビットを元に戻すことができない場合があります(たとえば、スーパーユーザーではない場合)。
  4. 最後に、我慢してコードを読んでください。長くて見づらいですが(見たところ)、信頼性が高く効率的です(使用中)。

これは長くて醜いですが、信頼性が高く効率的なソリューションです。

他の回答者が対処していないいくつかの問題を解決します。

  • シンボリックリンクを呼び出さないなど、シンボリックリンクを正しく処理しますshutil.rmtree()os.path.isdir()ディレクトリにリンクしている場合はテストに合格します。結果にos.walk()シンボリックリンクディレクトリも含まれます)。
  • 読み取り専用ファイルを適切に処理します。

これがコードです(唯一の便利な関数はですclear_dir()):

import os
import stat
import shutil


# http://stackoverflow.com/questions/1889597/deleting-directory-in-python
def _remove_readonly(fn, path_, excinfo):
    # Handle read-only files and directories
    if fn is os.rmdir:
        os.chmod(path_, stat.S_IWRITE)
        os.rmdir(path_)
    elif fn is os.remove:
        os.lchmod(path_, stat.S_IWRITE)
        os.remove(path_)


def force_remove_file_or_symlink(path_):
    try:
        os.remove(path_)
    except OSError:
        os.lchmod(path_, stat.S_IWRITE)
        os.remove(path_)


# Code from shutil.rmtree()
def is_regular_dir(path_):
    try:
        mode = os.lstat(path_).st_mode
    except os.error:
        mode = 0
    return stat.S_ISDIR(mode)


def clear_dir(path_):
    if is_regular_dir(path_):
        # Given path is a directory, clear its content
        for name in os.listdir(path_):
            fullpath = os.path.join(path_, name)
            if is_regular_dir(fullpath):
                shutil.rmtree(fullpath, onerror=_remove_readonly)
            else:
                force_remove_file_or_symlink(fullpath)
    else:
        # Given path is a file or a symlink.
        # Raise an exception here to avoid accidentally clearing the content
        # of a symbolic linked directory.
        raise OSError("Cannot call clear_dir() on a symbolic link")

ファイルモードの変更がどのような意味を持つのか理解できません。私のMacではos.remove、ユーティリティとは異なりrmあなたがファイルを所有している限り、読み取り専用ファイルを削除できます。一方、自分が所有していないファイルで、読み取り専用のアクセス権しか持っていない場合、そのファイルを削除したり、権限を変更したりすることはできません。システムで読み取り専用ファイルを削除できず、os.removeそのアクセス許可を変更できない状況はわかりません。さらに、lchmodそのドキュメントによれば、私のMacにもWindowsにも存在しないを使用しています。このコードはどのプラットフォーム向けですか?
Mark Amery

14

誰もpathlibこの仕事をするのに素晴らしいことを言っていないことに驚いています。

ディレクトリ内のファイルのみを削除する場合は、ワンライナーにすることができます

from pathlib import Path

[f.unlink() for f in Path("/path/to/folder").glob("*") if f.is_file()] 

ディレクトリを再帰的に削除するには、次のように記述します。

from pathlib import Path
from shutil import rmtree

for path in Path("/path/to/folder").glob("**/*"):
    if path.is_file():
        path.unlink()
    elif path.is_dir():
        rmtree(path)

1
.iterdir()代わりに動作する.glob(...)はずです。
S.カービー

12
import os
import shutil

# Gather directory contents
contents = [os.path.join(target_dir, i) for i in os.listdir(target_dir)]

# Iterate and remove each item in the appropriate manner
[os.remove(i) if os.path.isfile(i) or os.path.islink(i) else shutil.rmtree(i) for i in contents]

以前のコメントでは、Python 3.5以降でのos.scandirの使用についても言及されています。例えば:

import os
import shutil

with os.scandir(target_dir) as entries:
    for entry in entries:
        if entry.is_file() or entry.is_symlink():
            os.remove(entry.path)
        elif entry.is_dir():
            shutil.rmtree(entry.path)

1
os.path.isdir()通常のディレクトリとシンボリックリンクを区別する有効な方法ではありません。shutil.rmtree()シンボリックリンクを呼び出すと、OSError例外が発生します。
Rockallite 2014

@Rockalliteありがとう。あなたが正しい。例を更新しました。
Jacob Wan

8

あなたはos.walk()これのために使用する方が良いかもしれません。

os.listdir()ファイルとディレクトリを区別しないため、これらのリンクを解除しようとするとすぐに問題が発生します。使用しての良い例がありos.walk()、再帰的にディレクトリを削除するためにここに、そしてあなたの状況に適応させる方法についてのヒントが。


6

私はこの方法で問題を解決していました:

import shutil
import os

shutil.rmtree(dirpath)
os.mkdir(dirpath)

7
これは、質問が尋ねるものと根本的に異なるセマンティクスを持ち、有効な回答と見なされるべきではありません。
fatuhoku 2013

1
「ローカルフォルダーの内容を削除する」ことには、フォルダー自体を削除することは含まれないと思います。この回答と同じ問題ですが、賛成票がたくさんありました。
fatuhoku 2013

3
それは「Pythonで1を返す関数にどうすればよいですか?」という質問に答えるようなものです。def return_a_one():launch_some_nukes()return 1
fatuhoku

2
もちろん、セマンティクスは異なります。しかし、問題を調べる別の方法として検討することもできます。このソリューションは問題を解決するため、完全に有効です。「launch_some_nukes」の例とは異なります。1.解決策は受け入れられたものよりも短くて簡単であり、あなたが引用した答えとは対照的に、それは有効です。2.この場合の「launch_some_nukes」に相当するのは、フォルダーの削除と再作成です。古いフォルダと新しいフォルダの違いは、iノード番号のみです(おそらくOPには関係ありません)
ProfHase85

2
超高層ビルを解体し、まったく同じサイズを再構築しています;)
ProfHase85

5

さらに別のソリューション:

import sh
sh.rm(sh.glob('/path/to/folder/*'))

1
これshは標準ライブラリの一部ではないため、使用する前にPyPIからインストールする必要があります。また、これは実際rmにはサブプロセスで呼び出されるため、rm存在しないWindowsでは機能しません。フォルダにサブディレクトリが含まれている場合も例外が発生します。
Mark Amery

5

古いスレッドだと思いますが、pythonの公式サイトで面白いものを見つけました。ディレクトリ内のすべてのコンテンツを削除する別のアイデアを共有するためだけに。shutil.rmtree()を使用するときに承認の問題がいくつかあり、ディレクトリを削除して再作成したくありません。元のアドレスはhttp://docs.python.org/2/library/os.html#os.walkです。それが誰かを助けることを願っています。

def emptydir(top):
    if(top == '/' or top == "\\"): return
    else:
        for root, dirs, files in os.walk(top, topdown=False):
            for name in files:
                os.remove(os.path.join(root, name))
            for name in dirs:
                os.rmdir(os.path.join(root, name))

4

フォルダ自体を削除せずに、ディレクトリ内のすべてのファイルとそのサブディレクトリを削除するには、次のようにします。

import os
mypath = "my_folder" #Enter your path here
for root, dirs, files in os.walk(mypath):
    for file in files:
        os.remove(os.path.join(root, file))

3

* nixシステムを使用している場合は、systemコマンドを活用してみませんか?

import os
path = 'folder/to/clean'
os.system('rm -rf %s/*' % path)

3
質問で述べられているように、「現在のプロジェクトはWindows用です」
モニカのソックス

3

それを行うためのかなり直感的な方法:

import shutil, os


def remove_folder_contents(path):
    shutil.rmtree(path)
    os.makedirs(path)


remove_folder_contents('/path/to/folder')

3

まあ、私はこのコードが機能していると思います。フォルダーは削除されません。このコードを使用して、特定の拡張子を持つファイルを削除できます。

import os
import glob

files = glob.glob(r'path/*')
for items in files:
    os.remove(items)

3

単一の親ディレクトリ内の3つの別々のフォルダーからファイルを削除する必要がありました。

directory
   folderA
      file1
   folderB
      file2
   folderC
      file3

この単純なコードは私にとってトリックを作りました:(私はUnixを使っています)

import os
import glob

folders = glob.glob('./path/to/parentdir/*')
for fo in folders:
  file = glob.glob(f'{fo}/*')
  for f in file:
    os.remove(f)

お役に立てれば。


1

間にrmtree makedirs追加して問題を解決しましたtime.sleep()

if os.path.isdir(folder_location):
    shutil.rmtree(folder_location)

time.sleep(.5)

os.makedirs(folder_location, 0o777)

0

限られた特定の状況に対する回答:サブフォルダーツリーを維持しながらファイルを削除する場合は、再帰的アルゴリズムを使用できます。

import os

def recursively_remove_files(f):
    if os.path.isfile(f):
        os.unlink(f)
    elif os.path.isdir(f):
        for fi in os.listdir(f):
            recursively_remove_files(os.path.join(f, fi))

recursively_remove_files(my_directory)

少し話題から外れているかもしれませんが、多くの人が役に立つと思います


stackoverflow.com/a/54889532/1709587にos.walk示されている方法で使用することは、ディレクトリ構造をそのままにしてすべてのファイルを削除するより良い方法です。
Mark Amery

-1

temp_dir削除すると仮定すると、使用する単一行コマンドosは次のようになります。

_ = [os.remove(os.path.join(save_dir,i)) for i in os.listdir(temp_dir)]

注:これは、ファイルを削除するための1行のみですディレクトリを削除しません。

お役に立てれば。ありがとう。


-1

以下のメソッドを使用して、ディレクトリ自体ではなく、ディレクトリの内容を削除します。

import os
import shutil

def remove_contents(path):
    for c in os.listdir(path):
        full_path = os.path.join(path, c)
        if os.path.isfile(full_path):
            os.remove(full_path)
        else:
            shutil.rmtree(full_path)

@FabioSpaghetti Negative
Amir Rezazadeh

アミール、私はルートディレクトリのすべてのサブディレクトリで特定のフォルダーを見つけ、そのフォルダーの内容を削除するソリューションを探しています
FabioSpaghetti

これは、あなたがこれを投稿する前に受け入れられた回答年にまだ示されていない新しいものを追加しません。
Mark Amery

-1

フォルダ内のすべてのファイルを削除する/すべてのファイルを削除する最も簡単な方法

import os
files = os.listdir(yourFilePath)
for f in files:
    os.remove(yourFilePath + f)

サブディレクトリがある場合は失敗します。
Mark Amery

-3

これは、OSモジュールを使用して一覧表示してから削除するだけでうまくいくはずです!

import os
DIR = os.list('Folder')
for i in range(len(DIR)):
    os.remove('Folder'+chr(92)+i)

私のために働いた、どんな問題でも私に知らせた!

弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.