como remover arquivos em uma lista de caminhos facilmente?

5

Eu tenho uma lista de linhas como

/usr/lib/i386-linux-gnu/libavfilter.so
/usr/lib/i386-linux-gnu/libavfilter.so.3
/usr/lib/i386-linux-gnu/libavfilter.so.3.42.103
/usr/lib/i386-linux-gnu/i686/cmov/libavfilter.so
/usr/lib/i386-linux-gnu/i686/cmov/libavfilter.so.3
/usr/lib/i386-linux-gnu/i686/cmov/libavfilter.so.3.42.103
/usr/local/lib/libavfilter.so
/usr/local/lib/libavfilter.so.4
/usr/local/lib/libavfilter.so.4.4.100

Como posso remover esses arquivos completamente em vez de removê-los um por um como

 rm        /usr/lib/i386-linux-gnu/libavfilter.so
 rm        /usr/lib/i386-linux-gnu/libavfilter.so.3
 rm        /usr/lib/i386-linux-gnu/libavfilter.so.3.42.103
 rm        /usr/lib/i386-linux-gnu/i686/cmov/libavfilter.so
 rm        /usr/lib/i386-linux-gnu/i686/cmov/libavfilter.so.3
 rm        /usr/lib/i386-linux-gnu/i686/cmov/libavfilter.so.3.42.103
 rm        /usr/local/lib/libavfilter.so
 rm        /usr/local/lib/libavfilter.so.4
 rm        /usr/local/lib/libavfilter.so.4.4.100

?

AVISO! Não aplique os comandos abaixo sem verificar a saída no início

    
por kenn 09.07.2014 / 19:29

6 respostas

11

Qual sua opinião? Um arquivo? Um comando? De qualquer forma, xargs deve ser útil:

cat file | xargs rm

... irá apagar todos os caminhos de todas as linhas do arquivo. Se é apenas um comando que gera um caminho em cada linha, canalize-o através de xargs e ele deve funcionar bem.

Como alternativa, use xargs --arg-file="file.txt" rm . Isso economiza cachimbo e gato desnecessário .

Se você quer fazer mais com cada linha, você pode usar um tradicional bash while loop:

# uses echo for testing
# remove # before rm for actual deletion
while read -r path; do
    echo "deleting $path"
    # rm "$path"
done < file

Se a sua lista é a saída de find , você tem outras opções, incluindo a opção -delete ou o -exec rm {} \+ . Há quase certamente algumas dezenas de outras rotas viáveis para o sucesso. Se você está fazendo a exclusão automática com a localização, basta verificar a saída antes de excluir. Não vai te perdoar seus erros.

Os espaços podem ser um problema com as tarefas de tubulação em xargs . Isso pode não ser um problema para você e sua localização, mas os dois locate e xargs têm uma maneira de contornar isso. Eles podem optar por usar o caractere %code% null como um delimitador em vez de linhas de retorno. Yay. Em suma, seu comando se torna:

locate -0b libavfilter.so | xargs -0 rm
    
por Oli 09.07.2014 / 19:33
1

Canalize a saída para xargs :

echo "/usr/lib/i386-linux-gnu/libavfilter.so
/usr/lib/i386-linux-gnu/libavfilter.so.3
/usr/lib/i386-linux-gnu/libavfilter.so.3.42.103
/usr/lib/i386-linux-gnu/i686/cmov/libavfilter.so
/usr/lib/i386-linux-gnu/i686/cmov/libavfilter.so.3
/usr/lib/i386-linux-gnu/i686/cmov/libavfilter.so.3.42.103
/usr/local/lib/libavfilter.so
/usr/local/lib/libavfilter.so.4
/usr/local/lib/libavfilter.so.4.4.100" | xargs rm

Ou se sua lista estiver em um arquivo:

cat file | xargs rm
    
por chaos 09.07.2014 / 19:35
1

No nível básico, isso pode ser feito em Python:

import os

with open('input.txt') as f:
    for line in f:
        os.unlink(line.strip())

Caso você tenha nomes de arquivos exóticos (como criados com touch with$'\n'backslash ou with$'\n'newline , o que é uma ideia muito ruim, mas possível), você pode usar um arquivo de entrada da seguinte forma:

./with\backspace
./with\nnewline

E lide com tudo no Python 3 da seguinte forma:

import os

with open('./input.txt') as f:
    for l in f:
        # alternatively one can use 
        # bytes(l.strip(),sys.getdefaultencoding())
        bytes_filename =  bytes(l.strip(), 'utf-8').decode('unicode_escape')
        f_stat = os.stat(os.fsdecode( bytes_filename ) )
        print(l.strip(),f_stat)

Existe uma maneira de fazer isso em Python 2 também.

    
por Sergiy Kolodyazhnyy 09.09.2018 / 08:37
0

Você pode colocar os arquivos após um ao outro dividido por um espaço. Assim:

rm /usr/lib/i386-linux-gnu/libavfilter.so /usr/lib/i386-linux-gnu/libavfilter.so.3 /usr/lib/i386-linux-gnu/libavfilter.so.3.42.103        /usr/lib/i386-linux-gnu/i686/cmov/libavfilter.so /usr/lib/i386-linux-gnu/i686/cmov/libavfilter.so.3 /usr/lib/i386-linux-gnu/i686/cmov/libavfilter.so.3.42.103 /usr/local/lib/libavfilter.so /usr/local/lib/libavfilter.so.4 /usr/local/lib/libavfilter.so.4.4.100
    
por Rinzwind 09.07.2014 / 19:33
0

A maneira mais fácil é

cat list.txt | xargs -P 3 rm 

Enquanto você não pode usar -P, que por padrão executaria o maior número possível, mas isso pode ser um problema se sua lista for grande. Veja as páginas man para mais explicações.

Um lado negativo para isso, se seus arquivos tiverem espaço no nome, isso falhará. Se não foi esse o caso, você pode simplesmente usar, mas se houver arquivos com espaço no nome que você espera, de modo que, no caso, certifique-se de especificar o delimitador como caractere de nova linha.

cat list.txt | xargs -d '\n' -P 3 rm 

No Mac OS, isso produzirá um erro, mas você não está no Mac OS, por isso é bom usar isso.

Nota: Como isso é algo que pode causar perda de dados / configuração ou prejudicar sua instalação, é sempre recomendável que você use listar os arquivos antes de realmente removê-los. Use ls e, se os arquivos estiverem listados corretamente conforme o esperado, mude para rm.

    
por R J 09.09.2018 / 06:51
-2

use algo como o notepad ++, vá para substituir (ctrl + r) enter - > encontre o que: \ r \ n (verifique se o modo de pesquisa está definido como estendido) e substitua por: insira um espaço

então você tem tudo em uma linha

copie-o para um shell e digite rm -rf [cole o arquivo / fold-nomes do notepad ++ aqui]

    
por Klaus 08.03.2016 / 10:35

Tags