Encontrando diretórios vazios recursivamente

6

Como posso encontrar todos os diretórios vazios, digamos, em /home/.../Desktop. Como estou no Solaris, não posso usar o comando find . -empty -type d . Existe alguma outra maneira?

    
por Thodoris 12.12.2015 / 19:20

1 resposta

8

(Eu não tenho uma máquina Solaris à mão, então estou trabalhando em manpages, então você pode ter que brincar um pouco com a sintaxe aqui.)

Você pode usar o fato de que qualquer diretório vazio terá uma contagem de links de 2 (somente o nome do diretório, dir , além de seu próprio dir/. , link para ele); no UNIX, é ilegal vincular (hard) a um diretório, exceto no momento de adicioná-lo a uma entrada de diretório (única) ou ter entradas de diretório adicionadas a ele, portanto, isso é uma invariante. (Basicamente 1 .)

O Solaris não suporta a opção -empty , mas suporta a opção -links <n> para pesquisar coisas com exatamente n links. Então o comando que você quer (eu acho ; veja abaixo) é:

find /home/.../Desktop -type d -links 2 -print

a propósito ...

Seu uso da palavra "recursivamente" é um pouco ambíguo, então, por favor, note que isto não encontrará diretórios contendo apenas diretórios vazios (ou assim por diante, recursivamente). Se você quiser, a questão é muito fácil se você quiser identificá-los para deletá-los . Apenas execute repetidamente o comando acima, adicionando -exec rmdir {} \; até que nenhum seja deixado; cada vez que você executá-lo, você removerá os pais de árvores um nível mais profundo, portanto, ele não deve executar muitas execuções, a menos que você tenha uma árvore de diretórios profunda, consistindo apenas em diretórios vazios. (Dependendo de como o Solaris encontrar (1) funciona, eu acho que você também pode executar find . -type d -exec rmdir -p {}; apenas uma vez (a opção -p diz a rmdir (1) que ele pode remover diretórios contendo diretórios que estão vazios), mas como ele tentará atravessar os diretórios que foram deletados, você receberá um monte de mensagens de erro que você pode ignorar misturadas com aquelas com as quais você poderia se importar, então eu faria dessa maneira iterativa.)

(Observe que a opção -depth de find (1) não ajuda aqui, pois os arquivos stat () são muito cedo para a contagem de links Caso contrário, você poderia executar find -depth $dir -type d -links 2 -exec rmdir {} \; e uma execução seria suficiente.)

Se você quiser identificar ambos diretórios e diretórios "intrinsicamente vazios" contendo apenas diretórios vazios (ou assim por diante, recursivamente) sem removê-los, é mais complexo. Eu suponho que uma única linha de comando é possível, mas será uma fera (uma que eu tenho certeza de que alguém irá tentar mais tarde), pelo menos sem recorrer a perl ou um louco sed / awk encantamento .

Mas o que eu faço é copiar a árvore de diretórios em algum lugar, digamos / tmp / tree-copy , então execute o comando

find /tmp/tree-copy -type d -links 2 -print -exec rmdir {} \; | tee -a /tmp/empty-dirlist

repetidamente até que não produza mais saída. (O tee -a permite que você veja a saída, mas também a anexa ao arquivo / tmp / empty-dirlist .)

Você então deseja remover o /tmp/tree-copy ou o que quer que seja de cada linha do arquivo;

perl -i -lpe 's{^/tmp/tree-copy/}{}' /tmp/empty-dirlist

funcionará para isso, ou você pode usar o seu editor de texto. Voilà! , uma lista dos diretórios vazios, onde "vazio" é definido como "contendo apenas diretórios". (Você também pode colocar o perl ou sed ou qualquer outra coisa no pipeline antes do tee -a , se desejar.)

  1. Antes que alguns comentários apontem, isso não é necessariamente verdade para os pontos de montagem do sistema de arquivos ; Os gerenciadores do sistema de arquivos em alguns SOs estão livres para usar a contagem de links do ponto de montagem para seu próprio uso privado, portanto você verá frequentemente diretórios de pontos de montagem, vazios ou não, com contagens de links de 1 (ilegal para diretórios em outras circunstâncias) , 2 ou outra coisa significativa, mas não relacionada à contagem real de links. Então, se você for fazer o acima, você deve verificar se você não está potencialmente atravessando os pontos de montagem, pois é possível, embora improvável, que um deles tenha uma contagem de links de 2.
por 12.12.2015 / 21:57