Eu tenho uma coleção de arquivos (* .zip, * .txt, * .tar.gz, * .doc, ... etc). Esses arquivos residem em um caminho. Quero encontrar todos os arquivos (* .txt) e depois copiar apenas os arquivos de texto que contêm palavras específicas (por exemplo, LINUX / UNIX).
Eu executei o seguinte:
find . -name "*.txt" | grep 'LINUX/UNIX'
Este comando foi capaz de encontrar todos os arquivos de texto e, em seguida, "grep" filtrou os arquivos de texto resultantes, listando apenas os arquivos de texto que contêm 'LINUX / UNIX'.
Como posso copiar esses arquivos finais (ou seja, os arquivos de texto que contêm 'LINUX / UNIX') para um caminho específico de sua escolha?
Eu tentei aplicar xargs
find . -name "*.txt" | grep 'LINUX/UNIX' | xargs cp <to a path>
Mas não funcionou
Respostas:
Tentar:
Como esse comando usa a separação NUL, é seguro para todos os nomes de arquivos, incluindo aqueles com nomes difíceis, que incluem espaços em branco, guias ou até novas linhas.
O acima requer GNU
cp
. Para MacOS / FreeBSD, tente:Como funciona:
grep
opções e argumentos-r
diz ao grep para pesquisar recursivamente através da estrutura de diretórios. (No FreeBSD,-r
os links simbólicos serão seguidos nos diretórios. Isso não ocorre no OS / X ou nas versões recentes do GNUgrep
.)--include '*.txt'
diz ao grep para retornar somente arquivos cujos nomes correspondam ao glob*.txt
(incluindo nomes ocultos como.foo.txt
ou.txt
).-l
diz ao grep para retornar apenas os nomes dos arquivos correspondentes, não a correspondência em si.--null
diz ao grep para usar caracteres NUL para separar os nomes dos arquivos. (--null
É suportado porgrep
debaixo GNU / Linux , MacOS e FreeBSD mas não OpenBSD .)LINUX/UNIX
diz ao grep para procurar apenas arquivos cujo conteúdo inclua a expressão regularLINUX/UNIX
.
procure no diretório atual. Você pode omiti-lo nas versões recentes do GNUgrep
, mas precisará passar um--
terminador de opções paracp
se proteger dos nomes de arquivos que começam com-
.xargs
opções e argumentos-0
diz aos xargs que esperem entrada separada por NUL.-r
diz ao xargs para não executar o comando, a menos que pelo menos um arquivo tenha sido encontrado. (Esta opção não é necessária no BSD ou no OSX e não é compatível com o OSXxargs
.)cp -t /path/to/dest
copia os diretórios para o diretório de destino. (-t
requer GNUcp
.)fonte
cp -t
é apenas para Linux.--null
e adicionei uma versão para BSD / OSX que não usacp -t
.grep
não possui--null
.--null
.Mais portável (apenas recursos POSIX):
fonte
O seguinte liner sh / Bash one é outro método, embora só funcione no diretório atual e não seja recorrente:
A
-l
opção grep imprimirá uma lista dos arquivos que estão sendo copiados, embora você possa usá--q
lo se não quiser ver nada na tela.fonte
Não sei por que a string original não funcionou. O comando a seguir funciona para mim.
encontre / -name (nome do arquivo *) | grep '(filename.extention)' | xargs cp -t ./
No meu caso, filename * é uma coleção de arquivos com o mesmo nome e com diferentes tipos de arquivos (txt, zip, etc). Eu grep para descobrir apenas filename.txt e copiá-lo para o diretório de destino (que atualmente é ./).
fonte