O -depth
principal para fazer find
com que ele realize uma pesquisa profunda.
No entanto, a sequência padrão não é uma pesquisa pela primeira vez.
A sequência padrão pode ser descrita informalmente como uma "travessia profunda que trata de nós quando eles são encontrados pela primeira vez, em vez de fazê-lo durante o retorno".
Tenho uma necessidade real de primeira pesquisa de largura. Como posso me find
comportar dessa maneira?
Para ilustração, com a seguinte configuração:
$ mkdir -p alpha/{bravo,charlie,delta}
$ touch alpha/charlie/{alpha,beta,gamma,phi}
find
tem o seguinte comportamento padrão:
$ find alpha
alpha
alpha/charlie
alpha/charlie/alpha
alpha/charlie/phi
alpha/charlie/beta
alpha/charlie/gamma
alpha/delta
alpha/bravo
e com -depth
, ele executa da seguinte maneira:
$ find alpha -depth
alpha/charlie/alpha
alpha/charlie/phi
alpha/charlie/beta
alpha/charlie/gamma
alpha/charlie
alpha/delta
alpha/bravo
alpha
No entanto, o que eu quero é a seguinte opção (fictícia):
$ find alpha -bfs
alpha
alpha/charlie
alpha/delta
alpha/bravo
alpha/charlie/alpha
alpha/charlie/phi
alpha/charlie/beta
alpha/charlie/gamma
Em outras palavras, eu preciso find
processar / relatar todos os arquivos / diretórios em uma determinada profundidade antes de prosseguir.
Como posso fazer isso?
find
(pelo menos, não com apenasfind
). Deseja apenas listar os arquivos ou deseja usar outras primárias?-bfs
não seria exatamente o que eu precisava ... Eu tenho um script simples que gera um índice para um projeto GitLab grande, adequado para inclusão no Wiki do GitLab. Faz os cabeçalhos hierarquicamente com base nos nomes de diretório. Funciona muito bem, exceto que na estrutura do arquivo de exemplo acima, ela seria colocadadelta
nocharlie
subtítulo, em vez de noalpha
cabeçalho pai .find
saída é classificada em ordem alfabética. Não faço ideia porque ...-bfs
pode ser útil, mesmo que não se encaixe perfeitamente nesse caso de uso.Respostas:
Você pode fazer isso apenas com curingas de shell. Crie um padrão com progressivamente mais níveis de diretório.
Isso perde arquivos de ponto. Use
FIGNORE='.?(.)'
no ksh,shopt -s dotglob
no bash ousetopt glob_dots
no zsh para incluí-los.Ressalvas:
Se você quiser escolher a ordem ou os diretórios e os não diretórios, e o desempenho não for crítico, faça duas passagens e teste
[ -d "$file" ]
em cada passagem.fonte
*
. :)nullglob
e use(($#))
como condição de loop para evitar esse caso de borda.# cat ./bfind
Isso funciona aumentando a profundidade
find
e repetindo, acho que pode repetir resultados, mas pode ser filtrado facilmentefonte
Você pode colocar o seu
find
em uma classificação classificada principalmente pelo número de/
caracteres no nome do caminho. Por exemplo,Isso usa
awk
para prefixar o nome do caminho com o número de barras esed
para remover esse prefixo no final.Na verdade, como você provavelmente deseja que o conteúdo do diretório
alpha/charlie+
seja listado depoisalpha/charlie
, é necessário dizersort -t/ -k1,1 -k2,2 -k3,3 -k4,4
até a profundidade desejada.fonte
Outra resposta não baseada em 'find', mas no bash - use o "comprimento do diretório pai" primeiro e depois classifique por alfa.
A resposta não corresponde exatamente porque seus resultados têm "charlie, bravo, delta", mas imaginei se deveria ser "bravo, charlie, delta" em ordem alfabética.
Isso produz
fonte