Borulu komutları çalıştırırken Linux yardımcı programları akıllı mı?


23

Sadece bir terminalde birkaç komut çalıştırıyordum ve merak etmeye başladım, Unix / Linux boru komutları çalıştırırken kısayollar kullanıyor mu?

Örneğin, ilk 10'u içeren bir milyon satırlık bir dosyam var diyelim hello world. Komutu çalıştırırsanız, grep "hello world" file | headilk komut 10 satır bulur bulmaz durur mu yoksa önce tüm dosyayı aramaya devam eder mi?


2
Bu yüzden gnu grep tartışıyor -m.
Paul Tomblin

3
Terminalin bununla hiçbir ilgisi yok. Borulu komutlar kabuk tarafından yönetilir.
Keith Thompson

@KeithThompson cehaletimden dolayı özür dilerim, terminolojide büyük değilim, terminoloji, kabuk veya komut satırı olarak adlandırılacak mı emin değildim. Soruma düzenlemeler önermekten çekinmeyin :)
DisgruntledGoat

Yanıtlar:


30

Sırala. Kabuğun, çalıştırmakta olduğunuz komutların ne yapacağı hakkında hiçbir fikri yoktur, sadece birinin çıkışını diğerinin girişine bağlar.

Eğer grepbuluntular sonra "Merhaba dünya" demek 10'dan fazla satır headyakın boru istediği her 10 satır var ve olacaktır. Bu grepbir SIGPIPE ile ölüme neden olur , bu yüzden çok büyük bir dosyayı taramaya devam etmek zorunda kalmaz.


2
Öyleyse, yarış koşulları nedeniyle, grep zaten 11. ya da 12. modeli okumuş olabilirdi, ama muhtemelen 100 bininci değil mi?
kullanıcı bilinmeyen

3
Bu, kısmen hatların uzunluğuna ve boru tamponunun boyutuna bağlıdır, ancak kısa cevap grep'in öldürülmeden önce bir miktar makul miktarda ekstra veri okuyacağıdır.
dmckee,

1
@ userunknown, aynen.
psusi

Cool, bunun olduğunu bilmiyordum. grep/dev/null
İzkata'nın

15

Bir program bir boruya yazmaya çalıştığında ve o borudan okuma işlemi olmadığında, yazıcı programı bir SIGPIPE sinyali alır . Bir program SIGPIPE aldığında varsayılan eylem programı sonlandırmaktır. Bir program SIGPIPE sinyalini görmezden gelmeyi seçebilir, bu durumda yazma işlemi bir hata döndürür ( EPIPE).

Örnekte, işte olanların bir zaman çizelgesi:

  • grepVe headkomutlar paralel başlatmak.
  • grep bazı girdiler okur, işlemeye başlar.
  • Bir noktada, grepilk çıktı yığını üretir.
  • head ilk öbek okur ve yazar.
  • İlk 10 maçtan sonra yeterli satır olduğunu varsayarsak (aksi takdirde grepilk önce sonlanabilir), sonunda headistenen satır sayısını yazdırır. Bu noktada, headçıkar.
  • grepVe headişlemlerin nispi hızına bağlı olarak, grepbazı veriler birikmiş olabilir ve henüz yazdırılmamış olabilir. Zaman anda headçıkışlar, grepgiriş okuma ya da bunu yapmaya devam edeceğiz, bu durumda iç işleme yapıyor olabilir.
  • Yakında grepişlenen verileri yazacak. Bu noktada, bir SIGPIPE alacak ve ölecek.

Muhtemelen grepgerekenden biraz daha fazla girdiyi işlemesi muhtemel , ancak tipik olarak sadece birkaç kilobayt:

  • headgenellikle birkaç kilobaytlık parçalar halinde okur ( readher bayt için bir sistem çağrısı yapmaktan daha etkili olduğu için - bu davranışa tamponlama denir), bu nedenle istenen son satırın atılmasından sonraki son yığının geri kalanı atılır.
  • Borular çekirdek tarafından yönetilen birleşik bir ara belleğe sahip olduğundan (genellikle 512 bayt) geçiş sırasında bazı veriler olabilir. Bu veri atılacak.
  • grepçıkış öbek haline gelmeye hazır bazı veriler birikmiş olabilir (yeniden tamponlama). Çıkış tamponunu temizlemeye çalıştığında SIGPIPE alır.

Sistemin tamamında, filtre uygulamalarının doğal olarak verimli davranması için tam olarak tasarlanmıştır. Çıkış kanalları söndüğünde devam etmesi gereken programlar SIGPIPE sinyalini görmezden gelme adımını atmalıdır.


3

Sortof, boru hattı şu şekilde çalışır: önce sizin için ilk komutu, sonra ikinci komutu uygular.

Yani, A|Bverilen komut olalım . Sonra ister belirsizdir Aveya Bilk başlar. Birden fazla CPU varsa, tam olarak aynı anda başlayabilirler. Bir boru tanımsız fakat sınırlı miktarda veri tutabilir.

B borudan okumaya çalışır, ancak veri mevcut değilse B, veri gelene kadar bekleyecektir. Eğer Bbir diskten okuyordu, Bdisk bitirir okuyana kadar bekleyin için aynı sorun ve ihtiyaç olabilir. Daha yakın bir analoji klavyeden okunuyor olabilir. Orada, Bkullanıcının yazmasını beklemeniz gerekir. Ancak tüm bu durumlarda, B bir "okuma" işlemi başlattı ve bitinceye kadar beklemek zorunda. Fakat eğer Bbir komut ise , sadece giriş kısmına ulaşılan Abelirli bir noktadan sonra sadece kısmi bir çıktıya ihtiyaç duyarsa , SIGPIPE tarafından öldürülecektir.BA

Eğer Açalışır boruya yazma ve boru dolu, Aözgür olmak boru bazı oda için beklemek gerekir. Abir terminale yazıyorsa aynı sorunu yaşayabilirdi. Bir terminal akış kontrolüne sahiptir ve veri hızını ortalayabilir. Her durumda, için A, bir "yazma" işlemi başlattı ve yazma işlemi bitene kadar bekleyecek.

Ave Btüm eş işlemler, bir boru ile iletişim kuran, ancak, eş işlemleri gibi davranmak. Hiçbiri diğerinin tam kontrolünde değildir.


1
Soru şu: "B borunun tarafını kapattığında A ne yapar?"
enzotib

2
Bu 'kırık bir boru' olmaz mıydı?
Patkos Csaba

1
Bir program kapalı bir borudan / bu borudan okumaya / yazmaya çalışırsa (örneğin, headçıkışlar), programda bir SIGPIPE sinyali oluşur ve varsayılan davranış çıkmaktır.
Lekensteyn

Bu soruya tam olarak nasıl cevap veriyor? Görünüşe göre psusi'nin yanıtı daha kısa ve daha fazla.
jw013

1

grepborunun doğrudan kontrolü yoktur (sadece veri almaktadır) ve borunun doğrudan kontrolü yoktur grep(sadece veri gönderiyor) ...

Ne grepbaşka bir program yapar, ya da tamamen yukarı o programların iç mantığı etmektir. grepKomut satırı seçenekleriyle bulduğunuzda erken bir çıkış yapmasını söylerseniz , o zaman olacaktır, aksi takdirde kalıbı arayan dosyanın sonuna kadar sürüklenir ...

Terminal de aynı şekilde iç çalışmalarından grepve shellborulama eylemlerinden tamamen kopuktur ... Terminal temelde sadece bir fırlatma rampası ve çıkış ekranı ...

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.