Lidando com nomes de arquivos com primeiros caracteres especiais (ex. ♫)

Lidando com nomes de arquivos com primeiros caracteres especiais (ex. ♫)

Recentemente encontrei um arquivo cujo nome começa com o caractere '♫'. Eu queria copiar esse arquivo, alimentá-lo ffmpege referenciá-lo de várias outras maneiras no terminal. Normalmente preencho automaticamente nomes de arquivos estranhos, mas isso falha porque não consigo nem digitar a primeira letra.

Não quero mudar para o mouse para realizar uma manobra de copiar e colar. Não quero memorizar um monte de códigos para cenários possíveis. Minha solução ad hoc foi mudar para vim, colar !lse copiar o caractere em questão, depois sair e colá-lo no terminal. Isso funcionou, mas é horrível.

Existe uma maneira mais fácil de lidar com esses cenários?

OBSERVAÇÃO:Estou usando a casca do peixe se isso mudar as coisas.

Responder1

Se o primeiro caractere do nome do arquivo puder ser impresso, mas não for alfanumérico nem espaço em branco, você poderá usar [[:punct:]]o operador glob:

$ ls *.txt
f1.txt  f2.txt  ♫abc.txt
$ ls [[:punct:]]*.txt
♫abc.txt

Responder2

O mais simples que me ocorre é ls [^a-zA-Z0-9]*e funciona para mim, mas a resposta de Terdon é melhor para chamar a atenção para a opção extglob shell ou até mesmo para uma abordagem independente do shell.

Responder3

ls tem algumas opções (como --quote-name, --escape, --literal) para lidar com caracteres não imprimíveis, mas neste caso parece que o caractere é "imprimível", mas não "digitável" (pelo menos no meu teclado! ), então nenhuma dessas opções parece ajudar.

Portanto, como uma abordagem geral de "força bruta" para se livrar de arquivos com quaisquer caracteres em seus nomes, você pode fazer o seguinte:

$ /bin/ls -1A|cat -n  # list all files (except . and ..), 1 per line, add line numbers
     1  ♫
     2  f1.txt
     3  f2.txt

Encontre a linha que contém o arquivo incorreto. Muito provavelmente será a 1ª linha, mas digamos que seja a 5ª. Imprima a linha 5 e codifique-a em hexadecimal:

$ /bin/ls -1A|sed -n 5p|xxd -g 1
0000000: e2 99 ab 0a                                      ....

Ignorando o caractere 0a (nova linha), construa uma string de escape e use a opção -e de echo para traduzir os escapes:

$ echo -e '\xe2\x99\xab'

Agora você pode copiar/mover/excluir assim:

$ cp -vi $(echo -e '\xe2\x99\xab') better_name
‘♫’ -> ‘better_name’

Além disso, se você não estiver limitado a usar shell script, poderá fazê-lo em Python assim:

$ python
>>> import os
>>> os.listdir('.')
[ ..., '\xe2\x99\xab', ... ]
>>> print '\xe2\x99\xab'
>>> import shutil
>>> shutil.copy('\xe2\x99\xab', 'better_name')

Usando esta abordagem, você pode processar muitos arquivos, basta escrever a lógica para selecionar os arquivos corretos e renomeá-los sem sobrecarregar, etc:

for f in os.listdir('.'):
  if not f.isalnum():
    newname = generate_newname(f)
    if not os.path.exists(newname):
      shutil.copy(f, newname)
    else:
      print newname, 'already exists!'

Responder4

Renomear links simbólicos

Uma abordagem para lidar com nomes de arquivos com caracteres especiais - como primeiros caracteres ou em outro lugar no nome do arquivo érenomear para nomes mais simples.

Isso pode ser usado mesmo se você precisarmantenha os nomes dos arquivos originais: Renomeie uma cópia dos nomes dos arquivos.
Isso pode ser feito copiando os arquivos, mas também criandolinks simbólicos ou hardlinksaos arquivos e renomeie-os. cpcria links simbólicos em vez de cópias com a opção -s( -lpara hardlinks).

Use “detox” para limpar nomes

Para renomear para limpar nomes de arquivos,detoxpode ser usado; Ele renomeia arquivos para limpar nomes de arquivos de acordo com várias regras definidas em umdetoxrcarquivo. Por padrão, os caracteres UTF8 são apenas removidos; Com a opção -s utf_8-onlyeles são substituídos por _:

$ touch '♫ 漢字カ' ♫foo
$ ls -1
♫foo
♫ 漢字カ
$ detox -s utf_8-only * 
$ ls -1                
_ ___
_foo


"desintoxicação" em links simbólicos

Combinado com o trabalho em links simbólicos conforme descrito acima:

$ mkdir orig
$ cd orig 
$ touch '♫ 漢字カ' ♫foo
$ cd ..
$ mkdir clean
$ cd clean 
$ cp -s ../orig/* .
$ ll               
lrwxrwxrwx 1 14 Oct  8 05:52 ♫foo -> ../orig/♫foo
lrwxrwxrwx 1 21 Oct  8 05:52 ♫\ 漢字カ -> ../orig/♫\ 漢字カ
$ ls -1
♫foo
♫ 漢字カ
$ detox --special -s utf_8-only *
$ ll                                
lrwxrwxrwx 1 21 Oct  8 05:52 _\ ___ -> ../orig/♫\ 漢字カ
lrwxrwxrwx 1 14 Oct  8 05:52 _foo -> ../orig/♫foo

informação relacionada