neden ls -d de dosyaları listeler ve nerede belgelenmiştir?


48
  • ls --directory a*bunu belirtirken sadece ile başlayan dizinleri listelemelidira*
  • AMA dosya ve dizinlerden başlayarak listeler. a

Sorular :

  • Tamamen baktığımı düşündüğümden başka manve infonerede bazı belgeler bulabilirim ?
  • bu sadece BASH'da çalışır mı?


5
echo a*a(varsa) ile başlayan dosyaları da listeleyecektir . Sadece bunu yapıp yapmadığını daha açık hale getirmek için ls.
ash108

Yanıtlar:


89

a*Ve *a*sözdizimi vermeyerek, kabuk tarafından uygulanmaktadır lskomutu.

Ne zaman yaz

ls a*

Kabuk isteminde, kabuk a*, geçerli dizindeki adları ile başlayan tüm dosyaların listesini genişletir a. Örneğin a*, diziye genişleyebilir a1 a2 a3ve bunları argüman olarak iletebilir ls. lsKomut kendisi asla görür *karakteri; Sadece üç argüman görür a1, a2ve a3.

Joker karakter genişletme amaçları için "dosyalar", geçerli dizindeki tüm varlıkları ifade eder. Örneğin, a1normal bir dosya a2olabilir, bir dizin a3olabilir ve bir işaret olabilir. Hepsinde rehber girişi var ve kabuğun joker karakter genişletmesi bu girişlerin ne tür bir varlıktan bahsettiği ile ilgilenmiyor.

Pratikte rastlayacağınız tüm kabukları (bash, sh, ksh, zsh, csh, tcsh, ...) joker karakterler uygular. Ayrıntılar değişebilir, ancak *sıfır veya daha fazla karakter ?eşleştirmenin ve herhangi bir tek karakteri eşleştirmenin temel sözdizimi makul şekilde tutarlıdır.

Özellikle bash için, bu bash el kitabının "Dosya adı genişletme" bölümünde belgelenmiştir; çalıştırın info bashve "Dosya adı genişletme" ifadesini arayın veya buraya bakın .

Bunun kabuk tarafından ve bireysel komutlarla yapılmaması bazı ilginç (ve bazen şaşırtıcı) sonuçlara yol açar. Bu konuda en iyi şey, joker karakter işlemenin (hemen hemen) tüm komutlar için tutarlı olmasıdır ; eğer kabuk bunu yapmazsa, kaçınılmaz olarak bazı komutlar rahatsız olmaz ve diğerleri yazarın "daha iyi" olduğunu düşündüğü ustalıkla farklı şekillerde yapardı. (Windows komut kabuğunun bu sorunu yaşadığını düşünüyorum, ancak daha fazla yorum yapacak kadar aşina değilim.)

Öte yandan, birden fazla dosyayı yeniden adlandırmak için bir komut yazmak zor. Eğer yazarsan:

mv *.log *.log.bak

*.log.bakGeçerli dizinde zaten mevcut olan dosyalara göre genişletildiğinden , muhtemelen başarısız olacaktır . Böyle bir şey yapan komutlar var, ancak dosyaların nasıl yeniden adlandırılacağını belirlemek için kendi sözdizimlerini kullanmak zorundalar. Bazı komutlar (örneğin find) kendi joker karakter genişletmelerini yapabilir; kabuğun genişlemesini bastırmak için argümanlardan alıntı yapmalısınız

find . -name '*.txt' -print

Kabuğun joker genişlemesi, tamamen komut satırı argümanının sözdizimine ve mevcut dosya dizisine dayanır. O olamaz komutu anlamı etkilenebilir. Örneğin, tüm .logdosyaları ana dizine taşımak istiyorsanız, şunu yazabilirsiniz:

mv *.log ..

Eğer unutursanız ..:

mv *.log

ve .logşu anki dizinde tam olarak iki dosya var, genişleyecektir:

mv one.log two.log

Bu yeniden adlandırır one.logve clobber two.log.

EDIT : 52 yükseltme, bir kabul ve Guru rozeti sonrasında, belki de başlıktaki soruya cevap vermeliyim.

-dYa --directoryseçeneği lsyalnızca dizinleri listelemek için bunu söylemez. Dizinleri içeriklerini değil, kendileri gibi listelemelerini söyler. Dizine bir argüman adı verirseniz ls, varsayılan olarak dizinin içeriğini listeler , çünkü genellikle ilgilendiğiniz şey budur. -dSeçenek, sadece dizinin kendisini listelemesini söyler. Bu, joker karakterlerle birleştirildiğinde özellikle yararlı olabilir. Eğer yazarsanız:

ls -l a*

lsSize her birinin uzun bir liste verecek dosyanın adı başlar ile a, ve içerikleri adı başlar her dizinin a. Dosyaların ve dizinlerin listesini görmek istiyorsanız, her biri için bir satır kullanın:

ls -ld a*

hangi eşdeğerdir:

ls -l -d a*

Unutmayın ki lskomut asla *karakteri görmez .

Bunun belgelendirildiği yere gelince, Unix benzeri herhangi bir sistem hakkında komutun man lsbelgelerini size gösterecektir ls. Çoğu Linux tabanlı sistemlerde, lskomut GNU coreutils paketinin bir parçasıdır; Eğer varsa infokomutu ya info lsya info coreutils lssize daha fazla kesin ve kapsamlı bir dokümantasyon vermelidir. MacOS gibi diğer sistemler lskomutun farklı sürümlerini kullanabilir ve bu infokomutu kullanmayabilir; bu sistemler için kullanın man ls. Ve ls --helpbir gösterecektir nispeten kısa bir kullanım iletisi (sistemimde 117 hat) eğer sen GNU coreutils uygulamasını kullanıyoruz.

Ve evet, uzmanların bile dokümantasyona şimdi ve o zaman danışması gerekiyor. Ayrıca bu klasik şakayı görün .


8
@Thomas: Geçerli dizinde , adları ile başlayan a*tüm dosyaların listesine genişler . a
Keith Thompson,

2
@Tomolar: Veya belirttiğiniz dizinde:ls subdir/a*
Keith Thompson

1
Kabuk genişlemesinden sonra yürütülen komutu gerçekten görmek için, echoonu kullanın. Yani, ne zaman ne olduğunu bilmek istiyorsanız ls a*, ilk yürütmeecho ls a*
Carlos Campderrós

1
ya da sadece echo a*... kabuk yine de genişleme yapar
Yararsız

2
@sendmoreinfo: Bu kabuk ve ayarlara bağlıdır. Csh ve tcsh'de başarısız bir glob genişlemesi bir hatadır. Kısaca shopt -s failglob, aynı davranışa neden olur. Ayarlamak, nullglobancak değil failglob, örneğin, *nosuchfile*boş bir dizeye genişlemesine neden olur .
Keith Thompson

27

Keith Thompson'un cevabına bakınız; ancak neden ls --directory a*dosya ve dizinlerin gösterildiğini açıklamak için : --directorySeçenek, dizin olmayan dosyaları göstermez. Bunun yerine, dizinleri bu şekilde listeler, aksi halde içeriklerini listeler. Örnek:

$ mkdir foo
$ touch foo/bar
$ ls foo
bar
$ ls --directory foo
foo

3
Bu örnek -Fseçeneği ile daha çekici
glenn jackman

6

Çok açık olmak gerekirse, ls (1) kılavuz sayfasında belgelenmiştir :

-d, --dizin dizini içerik yerine dizin girişlerini gösterir ve sembolik bağları kaldırmaz

Dürüst olmak gerekirse, "içerik yerine girdiler" muhtemelen daha açıklayıcı olabilir:

DOSYA bir dizinse, o dizinin içeriğini listelemek yerine dizin girişini gösterin. DOSYA sembolik bir link ise, link ile gösterilen dosya yerine link girişini gösterin.


Soylu olmak gerekirse, man sayfasında -d seçeneği (aksi takdirde) açıklanabilirken, kabuk tarafından yapıldığı için argüman genişletme ve joker karakter, ls man sayfasında belgelenmez. Kabukunuzdaki dosya adı genişlemesini kapattıysanız, "ls a *" size yalnızca kelimenin tam anlamıyla 'a *' adlı bir dosyayı gösterir.
Johnny,

Soylu olmak için, kabuk genişlemesi diğer katılımcılar tarafından cevaplanırken, hiçbiri yetersiz açıklama ve bunun nasıl yanlış anlaşılabileceği konusunda konuşmuyor. Zaten iyi söylenenleri tekrar etmemi istersen, lütfen daha doğrudan davran.
msn

4

globbing

Açıklandığı gibi, Unix jargonunda *genişlemesine (ve benzer açılımlara) genişleme denir globve genellikle komut işlemcisinin bir özelliğidir (Unix parlance'daki "kabuk" olarak bilinir). Bu yüzden globbing başka birçok yerde de kullanılabilir; tipi man 7 globklasik bir Linux dağıtımının kabuk (veya bakınız bu ) hakkında daha fazla bilgi için globBing.

Unix'in başlarında glob, aslında adlı ayrı bir program uygulandı /etc/glob( bunun için dokümantasyon için bu eski UNIX kılavuzunun 10. sayfasına bakın ). Günümüzde, kod kütüphaneleri tarafından sağlanan bir kod rutinidir ve genellikle kabukları tarafından kullanılır. Kaynak : Wikipedia .

Dizinler

ls -dDosyaların yanı sıra dizinleri de listelediklerine gelince ...

lsAdam sayfa neden bu olur ama çok veciz açıklama ile açıklıyor. Yani burada genişletilmiş bir açıklama girişimi:

Varsayılan olarak lslistelerin içerikleri dizinlerin isimlerini verildiğinde ve aynı şeyi yapacak sembolik dizinlere. -dOpsiyon araçları (aynı zamanda verilebilir "adını dizinine (ler) (s) verildiğinde" örtülü tarafından globBing) , sadece dizinde (lar) ının _name_s gösteriyor ama değil içeriklerini. Benzer şekilde, dizinlere (açık veya dolaylı olarak ) sembolik isimler verildiğinde, referans aldığı dizinin içeriğini değil, sembolik bağlantının dosya adını gösterin.

Bu -dseçeneğin, hangi öğelerin listelendiği ile söyleyebileceğim kadarıyla hiçbir ilgisi yok ; : (kaynak bu yapılabilir burada birlikte) findşöyle: find . -maxdepth 1 -type d. Bunu sadece GNU ile yapmanın iyi bir yolu olup olmadığından emin değilim ls. İştefind komutun nasıl kullanılacağına dair bazı örnekler .

Özetle: Varsayılan olarak ls, yol adları verildiğinde dizinlerin içeriğini gösterir. -dStandart bir dosya için yapıldığı gibi, yalnızca dizin adını gösteren bu davranışı değiştirir.


3

Belgeler, yalnızca dizin girişlerini listelediğini söylemez; bunun yerine, içerik yerinels dir girişini listelediği dizin adını alır . Anlamanın en iyi yolu örnek:

> {ice} ~ :10:47 % ls -l / 
total 97
drwxr-xr-x   2 root root  4096 May  3 00:27 bin
drwxr-xr-x   4 root root  1024 May  3 14:17 boot
drwxr-xr-x   2 root root  4096 Apr 29 13:44 cdrom
drwxr-xr-x  18 root root  4420 May  9 09:58 dev
...
lrwxrwxrwx   1 root root    33 May  3 14:16 vmlinuz -> boot/vmlinuz-3.9.0-030900-generic
lrwxrwxrwx   1 root root    29 May  3 11:07 vmlinuz.old -> boot/vmlinuz-3.8.0-19-generic
> {ice} ~ :10:47 % ls -ld /
drwxr-xr-x 25 root root 4096 May  3 14:16 /

2

Belgeler kabuğun bir parçasıdır . Özellikle kabuk, bir komutu yerine getirmeden önce belirli bir sırada çeşitli açılımları ve ikameleri gerçekleştirir .

Dizisi kelime açılımları Bourne uyumlu kabuk olduğu

  1. Tilde Genişlemesi
  2. Parametre Genişletme
  3. Komut Değiştirme
  4. Aritmetik Genişleme
  5. Alan bölme
  6. Pathname Genişletme
  7. Alıntı Kaldırma

Böylece lskomut *karakterleri bile görmüyor , argümanlar zaten a*glob düzeniyle eşleşen tüm dosyalar ile genişletilmiş durumda . Bu, globbing dosya adına ihtiyaç duyan her komutun bu özelliği kendisi uygulamak zorunda olduğu Windows'takine benzemez.


1

İhtiyacınız olan anahtar kelime ( man bash) "Pathname Expansion" dır.


3
"Pathname Expansion" veya "Filename Generation" gibi. "Kalıp eşleştirme" ile ilgili, fakat aynı değil.
Stéphane Chazelas

@StephaneChazelas Aslında, ancak "desen eşleştirme", man sayfasındaki "yol adı genişlemesinin" bir alt bölümüdür, oysa "Dosya Adı Üretimi" burada hiç oluşmaz (sadece bilgi belgesinde).
Hauke ​​Laging,
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.