Linux betiğinde “okurken…” kullanma


34

Birisi lütfen aşağıdaki kodun nasıl çalıştığını açıklayabilir mi?

echo '1 2 3 4 5 6' | while read a b c
do
  echo $c $b $a
done

Özellikle, bu döngünün çıktısının neden iki ayrı satır 3 4 5 6 2 1yerine 3 2 1ve 6 5 4iki satırda olduğunu bilmek isterim. Aklımı etrafına saracak gibi görünmüyorum ...

Yanıtlar:


41

readstandart girdiden bir satır okur, satırı alanlara böler ve bu alanları verilen değişkenlere atar. Değişkenlerden daha fazla parça varsa, kalan parçalar son değişkene atanır.

Senin durumunda $aatanır 1, $batanır 2ve $ckalan 3 4 5 6.


Teşekkürler Florian! Şimdi mantıklı geliyor ... Bazı nedenlerden dolayı, boşlukların her değişken okumasını sınırlayacağını düşündüm, ama görünüşe göre değil. Yardımlarınız için teşekkür ederim!
linuxgringo

24

Döngüyü bu şekilde yeniden yazmak, neler olduğunu ortaya çıkarır:

echo '1 2 3 4 5 6' | while read a b c
  do
    echo '(iteration beginning)' a="$a" b="$b" c="$c" '(iteration ending)'
  done

Bu, çıktısı olarak verir:

(iteration beginning) a=1 b=2 c=3 4 5 6 (iteration ending)

İlk önce sadece bir yankı komutunun çalıştırıldığına dikkat edin. Birden fazla kez çalıştırılsaydı, diğer şeylerin yanı sıra, birden fazla basılan (iteration beginning)ve (iteration ending)alt dizileri de görürsünüz .

Bu, whileburada bir döngüye sahip olmanın gerçekten hiçbir şeyi gerçekleştirmediğini söylemek içindir . readYerleşiği boşluk ayrılmış metni okuma 1 her biri belirli bir değişkene. Ekstra giriş belirtilen son değişkenin sonuna eklenir. 2 Böylece değişkenler ave bdeğerleri alır 1ve 2sırasıyla değerleri calır 3 4 5 6.

Döngü koşulu (zaman while read a b c) ikinci kez değerlendirilir, (biz sadece tek bir metin satırı borulu) boru kullanılabilecek başka hiçbir giriş yok yani readkomut değerlendirir YANLıŞ yerine gerçek ve döngü durur (zamankinden yürütme vücut ikinci kez).

1 : Değişken isimleri argüman olarak iletildiğinde , readyerleşik ve teknik olmak gerekirse, girdi okur, IFS boşlukuyla karşılaştığında ayrı "kelimelere" ayırır (ayrıca bu soruya ve bu makaleye bakınız ).

2 : readEk giriş alanlarını belirtilen son değişkene sıkışma davranışı, ilk başta birçok komut dosyası için sezgisel değildir. Florian Diesch'in cevabının dediği gibi , readher zaman bir satırın tamamını okumaya çalışacağını - ve bunun readhem bir döngü hem de bir döngü olmadan kullanılabilir olması amaçlandığını düşündüğünüzde anlamak daha kolay hale gelir .


Eliah, tüm detayları açıklamaya zaman ayırdığınız için teşekkür ederiz. whileBu örnekte normal amacına hizmet etmediğinden şüphelenmiştim , ama sonra readkomut beni susturdu ... Bir şekilde, " read a b cyanlış olmasa da yap echo ..." olarak yorumladım . Gerçekten nasıl çalıştığını açıkladığınız için teşekkürler. Dün bu kodla karşılaştım ve çözene kadar beni
rahatsız

@linuxgringo Aslında, döngü gövdesi olan her yürütülecek read a b cdoğru olarak değerlendirilir ve döngü durumu ( read a b c) birden fazla kez çalıştırmak etmez. Bit sadece ilk kez doğru olarak değerlendirir . İkinci seferde, borudan okunacak başka girdi yok, bu nedenle dosyanın sonuna rastlanıyor ve yanlışread dönüyor . ( Kabuk komut dosyasında sıfırın doğru ve sıfırın yanlış olduğu anlamına gelmediğine dikkat çekerek, "Çıkış Durumu" nun çıktısının son bölümüne bakın .) Birden fazla girdi satırı için borulama yaparsanız , döngü gövdesi birden çok kez idam edilmek. help readwhile read ...
Eliah Kagan
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.