Encontre todos os arquivos com nome contendo string

177

Eu tenho procurado por um comando que retornará arquivos do diretório atual que contêm uma string no nome do arquivo. Eu vi locatee findcomandos que podem encontrar arquivos começando com algo first_word*ou terminando com algo *.jpg.

Como posso retornar uma lista de arquivos que contêm uma string no nome do arquivo?

Por exemplo, se 2012-06-04-touch-multiple-files-in-linux.markdownhavia um arquivo no diretório atual.

Como eu poderia retornar esse arquivo e outros que contenham a string touch? Usando um comando comofind '/touch/'

Dru
fonte
a pergunta é confusa. você deseja encontrar arquivos que contenham uma string ou arquivos cujos nomes contenham a string? a primeira pergunta é respondida com man grep, a segunda com man find. Por que você pesquisaria no Google em vez de usar o homem, não sei.
apenas alguém
1
Obrigado! A primeira frase não especificou se era o conteúdo do arquivo ou um nome de arquivo. Atualizada.
Dru

Respostas:

303

Use find:

find . -maxdepth 1 -name "*string*" -print

Ele encontrará todos os arquivos no diretório atual (exclua maxdepth 1se desejar, recursivo) contendo "string" e imprimi-lo na tela.

Se você quiser evitar o arquivo que contém ':', digite:

find . -maxdepth 1 -name "*string*" ! -name "*:*" -print

Se você quiser usar grep (mas acho que não é necessário, desde que você não queira verificar o conteúdo do arquivo), você pode usar:

ls | grep touch

Mas, repito, findé uma solução melhor e mais limpa para sua tarefa.

Zagorax
fonte
Obrigado @Zagorax. Isso faz exatamente. Desejo o comando não era tão longo, mas ayee :)
Dru
2
@Dru, modificado para cobrir o caso, se você quiser evitar dois pontos. findé uma ferramenta muito poderosa, deve ser de alguma forma 'longa'. :)
Zagorax
Obrigado, o primeiro fez isso perfeitamente, sem retornar nenhum conteúdo.
Dru
3
@Dru, se você quiser 'mais curto', poderá evitar, -printpois esse é o comportamento padrão e .a pasta padrão em que ele verifica.
Zagorax
1
find . -name "*string*"Funciona muito bem também. Remover .gera um erro do meu lado. Mais uma vez obrigado @Zagorax.
Dru
14

Use grep da seguinte maneira:

grep -R "touch" .

-Rsignifica recuar. Se você preferir não entrar nos subdiretórios, pule-o.

-isignifica "ignorar maiúsculas e minúsculas". Você pode achar que vale a pena tentar também.

carlspring
fonte
Ótimo. Notei que alguns conteúdos de arquivos seguem a :. Existe alguma maneira de reter isso? Usando uma opção, talvez?
Dru
1
Tente:grep -R "touch" . | cut -d ":" -f 2
carlspring
Isso parece produzir apenas o conteúdo dos arquivos. Você essencialmente respondeu minha pergunta, porém, eu posso tentar cavar um pouco para reter o conteúdo.
Dru
Ah ... você só precisa dos nomes dos arquivos? Execute: grep -R "touch" . | cut -d ":" -f 1 (desculpe, deve ter interpretado mal você).
Carlpring
Obrigado @carlspring isso é interessante. grepou retorna arquivos com conteúdo e nomes de arquivos que contêm touchou que contêm touch, ainda não tenho certeza de qual é o caso. Da lista de arquivos retornados, metade contém touchno título e a outra metade contém touchno corpo, não o título. Apenas percebi isso.
Dru
5

A -maxdepthopção deve estar antes da -nameopção, como abaixo.,

find . -maxdepth 1 -name "string" -print
Sunil Dias
fonte
1
Você deve colocar * antes e depois da "string".
Aerin
3
find $HOME -name "hello.c" -print

Isso pesquisará todo o sistema $HOME(ie /home/username/) por qualquer arquivo chamado “hello.c” e exibirá seus nomes de caminho:

/Users/user/Downloads/hello.c
/Users/user/hello.c

No entanto, não corresponderá HELLO.Cou HellO.C. Para corresponder à distinção entre maiúsculas e minúsculas, passe a -inameopção da seguinte maneira:

find $HOME -iname "hello.c" -print

Saídas de amostra:

/Users/user/Downloads/hello.c
/Users/user/Downloads/Y/Hello.C
/Users/user/Downloads/Z/HELLO.c
/Users/user/hello.c

Passe a -type fopção para procurar apenas arquivos:

find /dir/to/search -type f -iname "fooBar.conf.sample" -print
find $HOME -type f -iname "fooBar.conf.sample" -print

O -inamefunciona tanto on GNU ou BSD (incluindo OS X) de comando versão achado. Se sua versão do comando find não suportar -iname, tente a seguinte sintaxe usando o grepcomando:

find $HOME | grep -i "hello.c"
find $HOME -name "*" -print | grep -i "hello.c"

OU tente

find $HOME -name '[hH][eE][lL][lL][oO].[cC]' -print

Saídas de amostra:

/Users/user/Downloads/Z/HELLO.C
/Users/user/Downloads/Z/HEllO.c
/Users/user/Downloads/hello.c
/Users/user/hello.c
shilovk
fonte
0

Se a sequência estiver no início do nome, você poderá fazer isso

$ compgen -f .bash
.bashrc
.bash_profile
.bash_prompt
Steven Penny
fonte
3
compgennão é um martelo apropriado para esta unha. Essa ferramenta pouco usada foi projetada para listar comandos disponíveis e, como tal, lista arquivos no diretório atual (que podem ser scripts) e não pode recursar nem olhar além do início de um nome de arquivo nem pesquisar o conteúdo do arquivo, tornando-o principalmente inútil.
msanford
0

Uma alternativa para as muitas soluções já fornecidas é fazer uso do glob **. Quando você usa bashcom a opção globstar( shopt -s globstar) ou utiliza zsh, você pode simplesmente usar o glob **para isso.

**/bar

faz uma busca recursiva de diretório por arquivos nomeados bar(incluindo potencialmente o arquivo barno diretório atual). Observe que isso não pode ser combinado com outras formas de globbing no mesmo segmento de caminho; nesse caso, o* operadores retornam ao seu efeito usual.

Observe que há uma diferença sutil entre zshe bashaqui. Enquanto bashatravessará links diretos para diretórios, zshnão passará. Para isso, você tem que usar o glob ***/no zsh.

kvantour
fonte
0
find / -exec grep -lR "{test-string}" {} \;
Shahid
fonte
1
Esta resposta foi sinalizada por baixa qualidade. Explique o que as alterações propostas fazem.
Miroslav Glamuzina
-2
grep -R "somestring" | cut -d ":" -f 1
Saurabh kukade
fonte
2
Parece ser uma resposta para uma pergunta diferente - mas como você não forneceu nenhuma explicação, isso não é óbvio para o solicitante ou para qualquer outra pessoa.
Toby Speight