Enumere arquivos e diretórios com o comando 'ls'

11

Execute o comando lsno diretório atual e obtenha a saída:

$ ls
Applications Documents    Library      Music        Public
Desktop      Downloads    Movies       Pictures

Eu gostaria de enumerá-los como:

1. Applications
2. Desktop
3. Documents
4. Downloads
5. Library
6. Movies
7. Music
8. Pictures
9. Public

Isso pode ser alcançado usando de lessmaneira intermediária

ls | less -N

Como enumerá-los de maneira direta?

Cálculo
fonte
Você quer que isso sempre aconteça, ou apenas algumas vezes? No primeiro caso, você pode criar um alias de ls para um dos comandos nas respostas; no segundo, crie um novo alias - diga "lsn" ao comando.
Jamesqf 26/03

Respostas:

16

Ou simplesmente faça:

ls -b |nl -s '. ' -w 1
1. a\ file\ with\ nonewline
2. a\ file\ with\nnewline
3. a\ file\ with\ space
4. afile

de man nl:

-s, --number-separator=STRING
              add STRING after (possible) line number
-w, --number-width=NUMBER
              use NUMBER columns for line numbers
αғsнιη
fonte
13

Você deve canalizar a saída lspara outro comando. Minha sugestão é usar awkna desta forma :

$ ls -b --group-directories-first | awk '{print NR ". " $0}'
1. dir1
2. dir2
3. dir3
4. z-dir1
5. z-dir2
6. z-dir3
7. file1
8. file2
9. file3
10. file4
11. file5
12. file6
13. file7
14. file\nnewline
  • Observe que o arquivo file\nnewlinecontém um caractere de nova linha \nem seu nome que é escapado pela opção -b.

  • a opção --group-directories-firstexibirá os diretórios antes dos arquivos.

Outra maneira possível é usar o loop for (mas, neste caso, colocar os diretórios no início da lista se tornará mais difícil):

n=1; for i in *; do echo $((n++)). $i; done
pa4080
fonte
11

se apenas mostrar um número for o caso, você terá várias opções, bem como o seu less -Ncaminho:

$ ls |cat -n
$ ls |nl

Se você quiser numeração de saída personalizada, sugiro usar finde fazer o que quiser imprimir:

find . -exec bash -c 'for fnd; do printf "%d. %s\n" "$((++i))" "$fnd"; done ' _ {} +

POSIXly, você faria:

find . -exec sh -c 'for fnd; do i=$((i+1)); printf "%d.\t%s\n" "$i" "$fnd"; done ' _ {} +
αғsнιη
fonte
Nesse caso, ideve ser inicializado com antecedência:i=0; find ...
rexkogitans 26/03
isso não é necessariamente aqui, pois ele -exec sh -c '....' está sendo executado sob um shell sh separado.
αғsнιη
3

Você também pode fazer isso inteiramente com um pequeno script do Bash:

#!/bin/bash
set -eu
shopt -s nullglob

[ "$#" -eq 0 ] || cd -- "$1"
i=0
for f in *; do
    printf '%d. %s\n' "$((++i))" "${f//$'\n'/^N}"
done |
cat -vt

Você pode até ser chique e digitar o número da linha para obter mais de 9 resultados:

#!/bin/bash
set -eu
shopt -s nullglob

[ "$#" -eq 0 ] || cd -- "$1"
ls=(*)
pad=${#ls[@]}
pad=${#pad}
i=0
for f in *; do
    printf '%*d. %s\n' "$pad" "$((++i))" "${f//$'\n'/^N}"
done |
cat -vt

Uso

Supondo que você salvou o script como um arquivo executável numbered-ls.shno diretório de trabalho atual:

./numbered-ls.sh [DIRECTORY]

O argumento DIRECTORYé opcional e o padrão é o diretório de trabalho atual.

Explicação

  1. Se o script foi chamado com um argumento, altere o diretório de trabalho para o caminho no primeiro argumento.

  2. Combine todas as entradas do diretório de trabalho atual e examine-as. Para cada entrada, incremente um contador e imprima seu valor junto com o nome da entrada. Os caracteres de quebra de linha no nome da entrada são substituídos por ^N.

  3. Canalize a saída cat -vtpara lidar normalmente com nomes de arquivos que contêm caracteres não imprimíveis que o terminal pode interpretar como caracteres de controle.

David Foerster
fonte