Geçersiz karakterler dosya adlarından nasıl çıkarılır?


47

Bunun gibi geçersiz karakter içeren dosyalarım var

009_-_�%86ndringshåndtering.html

ÆDosya adında bir şeyler ters gitti.

Tüm geçersiz karakterleri silmenin bir yolu var mı?

veya bir trşekilde kullanılabilir mi?

echo "009_-_�%86ndringshåndtering.html" | tr ???

5
Karakterler muhtemelen "geçersiz" değildir, aksi halde dosya sistemi bunları saklamaz ( FS'ye gerçekten kötü bir şey yapmazsanız ). Adları doğru görüntülemek için yerel ayarlarınızı değiştirmeyi (örneğin UTF8) denediniz mi?
James O'Gorman

Yanıtlar:


41

Bir yol sed ile olurdu:

mv 'file' $(echo 'file' | sed -e 's/[^A-Za-z0-9._-]/_/g')

fileElbette, dosya adınızla değiştirin . Bu, bir harf, sayı, nokta, alt çizgi veya kısa çizgi olmayan herhangi bir şeyin yerine geçer. İstediğiniz gibi tutmak için karakter ekleyebilir veya kaldırabilir ve / veya değiştirilen karakteri başka bir şeyle veya hiç bir şeyle değiştirebilirsiniz.


4
Ben kullandım:f='file'; mv 'file' ${f//[^A-Za-z0-9._-]/_}
Louis

1
Aşağıdaki H. Hess tarafından en iyi çözümü arayın ... (ve yanımda komik yorumumu :))
Jan Sila

31

Linux kutusunda olduğunuzu ve dosyaların bir Windows kutusunda yapıldığını varsayıyorum. Linux, dosya adları için karakter kodlaması olarak UTF-8'i kullanırken, Windows başka bir şey kullanır. Bence sorunun nedeni bu.

"Convmv" kullanırdım. Bu, dosya adlarını bir karakter kodlamasından diğerine dönüştürebilen bir araçtır. Batı Avrupa için bunlardan biri normal olarak çalışır:

convmv -r -f windows-1252 -t UTF-8 .
convmv -r -f ISO-8859-1 -t UTF-8 .
convmv -r -f cp-850 -t UTF-8 .

Debian tabanlı bir Linux üzerine kurmanız gerekiyorsa bunu çalıştırarak yapabilirsiniz:

sudo apt-get install convmv

Her zaman benim için çalışıyor ve orijinal dosya adını kurtarır.

Kaynak: LeaseWebLabs


1
Bu umut verici görünüyor, ama kodlamanın ne olduğunu nasıl söyleyeceğin hakkında bir fikrin var mı? Save the current file in Word 97-2004 format\sco.workflowMac'imde (Microsoft Office aracılığıyla) oluşturulan bir dizinim var ve yukarıdaki kodlamanın bir etkisi olmaz.
Sridhar Sarnobat

Convmv'nin varsayılan olarak sadece kuru çalıştırma yaptığı ve hangi dosyaların taşınacağını söylediği "test" modunda çalıştığını belirtmek önemlidir. Daha sonra --notestdosyaları gerçekten yeniden adlandırmak seçeneğiyle tekrar çalıştırmanızı söyleyecektir .
Kenny Rasschaert

16

Diyelim ki dosya sistemini geçmek ve tüm bu dosyaları düzeltmek mi istiyorsunuz?

İşte böyle yaparım

find /path/to/files -type f -print0 | \
perl -n0e '$new = $_; if($new =~ s/[^[:ascii:]]/_/g) {
  print("Renaming $_ to $new\n"); rename($_, $new);
}'

Bu, ascii olmayan karakterlere sahip tüm dosyaları bulur ve bu karakterleri underscores ( _) ile değiştirirdi . Ancak yeni adı olan bir dosya varsa, üzerine yazacaktır. Betik böyle bir durumu kontrol etmek için değiştirilebilir, ancak bunu basit tutmak için eklemedim.


13

Https://stackoverflow.com/questions/2124010/grep-regex-to-match-non-ascii-characters adresindeki cevapları takip ederek , Kullanabilirsiniz:

rename 's/[^\x00-\x7F]//g' *

Yeniden *adlandırmak istediğiniz dosyaları eşleştiriyor. Birden fazla klasör üzerinde yapmak istiyorsanız, şöyle bir şey yapabilirsiniz:

find . -exec rename 's/[^\x00-\x7F]//g' "{}" \;

-N argümanını renamekuru bir işlem yapmak için kullanabilir ve neyin değişeceğini görmeksizin neyin değişeceğini görebilirsiniz.


Örneğin ü ve ä gibi yabancı karakterleri saklamak için bunu değiştirmenin bir yolu var mı?
Elder Geek

Sadece ikincisi benim için çalıştı. Her şey aynı dizinde olduğu için aradaki farkın ne olduğundan emin değilim ..?
Shautieh

1
@Shautieh: -n gerçekte çalışmasını engeller. Cevabı açıklığa kavuşturacağım.
naught101

Yeniden adlandırmak, çok sayıda dosyayla ilgilenirken yavaş olabilir. Bunu hızlandırmak istiyorsanız, kontrolü bulmak için kontrol düğmesine basın. Yine de nasıl yapılacağından emin değilim.
isaaclw

13

Kırık dosya adlarına sahip, bozuk bir usb bellekten kurtarılan bazı japon dosyalarım vardı ve yukarıdaki çözümler benim için işe yaramadı.

Detoks paketini tavsiye ederim:

Detoks yardımcı programı, çalışmayı kolaylaştırmak için dosyaları yeniden adlandırır. Boşlukları ve diğer sıkıntıları giderir. Ayrıca 8 bitlik ASCII ile kodlanmış Latin-1 (ISO 8859-1) karakterlerini, UTF-8 ile kodlanmış Unicode karakterlerini ve CGI çıkış karakterlerini de çevirir veya temizler.

Örnek kullanım:

detox -r -v /path/to/your/files
-r Alt dizinlere yineleme
-v Hangi dosyaların yeniden adlandırıldığına dair ayrıntılı bilgi edinin. 
-n Kuru çalışma için kullanılabilir (yalnızca neyin değiştirileceğini gösterin)

2
Bu çok daha yüksek olmalı, herkesi detoxesasen tekerleği yeniden icat etmeden önce bakmaya çağırıyorum . Man sayfasına bakarsanız, esnekliği nedeniyle burada önerilen diğer tüm çözümleri kapsadığını göreceksiniz.
emk2203

Hezekiel 25:17 - Kutsanmış olan, hayırseverlik ve iyilik adına bu çözümü kızdıracak, çünkü gerçekten kardeşinin koruyucusu ve kayıp çocukların bulucusu.
Jan Sila

Tuhaf bir şekilde, yol '' olamaz. Debian’da Eğer '.' Kullanıyorsanız hiçbir şey bulamaz.
isaaclw

Gerçekten işe yarayıp yaramadığını merak ediyorum, örneğin Çince karakterleri kaldır / değiştir gibi görünüyor 的节奏啊, ancak bu karakterler geçerli dosya adı.
林果皞

5

Bu kabuk betiği, dosyaları Linux / Windows ve FAT / NTFS / exFAT arasında taşınabilir hale getirmek için yinelenen bir dizini temizler. Kontrol karakterlerini /:*?"<>\|ve benzeri bazı ayrılmış Windows adlarını kaldırır COM0.

sanitize() {
  shopt -s extglob;

  filename=$(basename "$1")
  directory=$(dirname "$1")

  filename_clean=$(echo "$filename" | sed -e 's/[\\/:\*\?"<>\|\x01-\x1F\x7F]//g' -e 's/^\(nul\|prn\|con\|lpt[0-9]\|com[0-9]\|aux\)\(\.\|$\)//i' -e 's/^\.*$//' -e 's/^$/NONAME/')

  if (test "$filename" != "$filename_clean")
  then
    mv -v "$1" "$directory/$filename_clean"
  fi
}

export -f sanitize

sanitize_dir() {
  find "$1" -depth -exec bash -c 'sanitize "$0"' {} \;
}

sanitize_dir '/path/to/somewhere'

Linux teoride daha az kısıtlayıcıdır ( /ve \0dosya isimlerinde kesinlikle yasaktır) ancak pratikte birkaç karakter bash komutlarına müdahale eder (gibi *...) bu yüzden dosya isimlerinden de kaçınılmalıdır.

Dosya adlandırma kısıtlamaları için harika kaynaklar:


1
Aradığım şey bu! ancak boşluk bulunan dirtleri desteklemek için tırnak işaretleri ekleyin "$ 1" -depth -exec bash -c 'sanitize "$ 0"' {} \;
mmv-ru


0

Altyazı dosyalarındaki geçersiz karakterleri kaldırmak için bu tek astarı kullanıyorum:

for f in *.srt; do nf=$(echo "$f" |sed -e 's/[^A-Za-z0-9.]/./g' |sed 's/\.\.\././g' |sed 's/\.\././g'); test "$f" != "$nf" && mv "$f" "$nf" && echo "$nf"; done
  1. Yalnızca * .srt dosyalarını işle (*, her dosyayı işlemek için * .srt yerine kullanılabilir)
  2. A-Za-z harfleri, 0-9 arası sayılar ve "" ifadeleri dışındaki tüm karakterleri kaldırır.
  3. Olası çift veya üçlü dönemleri kaldırır
  4. Dosya adının geçersiz karakterleri olup olmadığını kontrol eder.
  5. True olursa, dosyayı mv komutuyla yeniden adlandırır, ardından echo komutuyla yaptığı değişiklikleri çıkarır

-2

* içindeki dosya için; mv "$ dosya" $ (eko "$ dosya" | | sed -e 's / [^ A-Za-z0-9. -] / / g'); bitti


2
Kodunuzun ne yaptığını açıklamalı ve doğru biçimlendirme kullanmalısınız. Kodunuz, adlara çarpışmalar eklenerek dosyaların silinmesine neden olabilir. Ve her şeyi arka planda çalıştırmak biraz saçma.
kasperd
Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.