テキストファイルにリストされているファイルを削除する方法


23

さまざまなファイルへのパスのリストがあるテキストファイルがあります。各行を反復処理し、指定されたパスにあるファイルを削除するコマンドを使用できますか?

回答:


33

使用xargs

xargs rm < file  # or
xargs -a file rm

ただし、ファイル名/パスにエスケープする必要のある文字が含まれている場合は機能しません。

ファイル名に改行がない場合は、次を実行できます。

tr '\n' '\0' < file | xargs -0 rm # or
xargs -a file -I{} rm {}

または、次のスクリプトを作成できます。

#!/bin/bash

if [ -z "$1" ]; then
    echo -e "Usage: $(basename $0) FILE\n"
    exit 1
fi

if [ ! -e "$1" ]; then
    echo -e "$1: File doesn't exist.\n"
    exit 1
fi

while read -r line; do
    [ -n "$line" ] && rm -- "$line"
done < "$1"

として保存し/usr/local/bin/delete-from、実行権限を付与します。

sudo chmod +x /usr/local/bin/delete-from

次に、それを実行します:

delete-from /path/to/file/with/list/of/files

2
本当にきれいな答えcatですが、必須ではありません。stdinリダイレクトを使用できます< file xargs rm
。-コス

フォルダの名前を分割し、それらを探します。たとえば、MY FOLDERは「MY」および「FOLDER」として解釈されていますか?
-daka

@sudoman回答が更新されました。
エリック

ファイルにスペースがない場合は、bashの「rm-$(cat file)」またはcat file(ba)shまたはcshの「rm- 」だけで済みます。
shooper

先ほどcat述べたように、@ shooper は役に立ちませstdinん。彼の更新された答えを見てください
コス

20

空白、バックスラッシュ、その他の奇妙な文字を含むファイル名を処理できる1つの方法を次に示します。

while read -r file; do rm -- "$file"; done < list.txt

の各行が読み込まlist.txtれ、保存され$file、実行さrmれます。これ-rにより、バックスラッシュが文字どおりに読み取られるようになります(つまり、TABではなくa とaに\t一致します)。それがまた始まるファイル名を扱うことを保証します。\t---

Perlでこれを行うこともできます。

perl -lne '$k{$_}++; END{unlink for keys(%k)}' list.txt

これは、各ファイル名を%kハッシュに読み込んでから、それぞれunlinkを削除するために使用します。


10

Python経由。

import sys
import os
fil = sys.argv[1]
with open(fil) as f:
    for line in f:
        os.remove(line.rstrip('\n'))

likeという名前のファイルに上記のスクリプトを保存し、script.pyターミナルで以下のコマンドを実行してスクリプトを実行します。

python3 script.py file

file は、実際に削除するファイルのパスが保存されている入力ファイルです。


6
ああ、少なくともあなたはPythonの答えを投稿する勇気を持っている:)
ジェイコブVlijm


2

これを行う別の方法:

ファイルをシェルスクリプトにすることで、ファイルを「準備」できます。

$ sed -E "s/^(.*)$/rm '\1'/" input_file
rm 'file1'
rm 'file2'
rm 'file with some spaces.ext'

ファイル名に一重引用符(')が含まれている場合は、このわずかに拡張されたバージョンを使用して、最初にそれらをエスケープできます。

$ sed -E "s/'/'\\\''; s/^(.*)$/rm '\1'/" input_file
rm 'file1'
rm 'file2'
rm 'file with some spaces.ext'
rm 'a file with "quotes"'
rm 'a file with '\''quotes'\'''

そして、次のようにパイプすることでこれを実行できますsh

$ sed -E "s/'/'\\\''; s/^(.*)$/rm '\1'/" input_file | sh

1

私が理解しているように、完全なパスを持つファイルを含むテキストファイルがあります。次の2つの可能性があります。

  1. リストには、改行で区切られたファイル名があります。つまり、各行にはファイルへの完全なパスがあります。この場合:ここに簡単な方法があります:

    for i in $(cat listOfFiles.txt); do
        rm -f $i
    done
    
  2. リストにスペースまたはタブで区切られた1行以上のファイル名がある場合、ドリルは次のとおりです。

    sed -i 's/\s\+/\n/g' listOfFiles.txt
    

    これにより、すべての空白が改行に変換されます

    for i in $(cat listOfFiles.txt); do
        rm -f $i
    done
    

はい、それを実現する方法はたくさんありますが、これは非常に簡単なアプローチです。

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