Ders 19 / 24
Kesme, Yapıştırma ve Bölme
Sütun kesme ve sınırları, dosyaları yan yana yapıştırma, karakter düzeyi dönüştürme, dosyayı parçalara bölme ve araç seçimi ölçütü.
İçindekiler
Önceki derslerin araçları satır düzeyinde çalıştı: satır seçtiler, satır dönüştürdüler, satır sıraladılar. Sütun düzeyinde kesme, iki dosyayı yan yana getirme, karakter düzeyi eşleme ve büyük bir dosyayı parçalara bölme ayrı bir araç öbeği gerektirir.
Bu ders o öbeği tanıtır ve metin işleme konusunu, hangi işin hangi araca ait olduğunu belirleyen bir ölçütle kapatır.
Sütun Kesme
cut bu kursta ilk dersten beri kullanılıyor. İki kipi vardır: alan kipi (-d ve -f)
ve karakter kipi (-c).
head -2 erisim.log | cut -d' ' -f1,7,9
10.0.0.12 /index.html 200 10.0.0.31 /statik/stil.css 200
head -2 erisim.log | cut -c1-11
10.0.0.12 - 10.0.0.31 -
Karakter kipi sabit genişlikli çıktılarda — hizalanmış tablolarda, sabit alanlı kayıtlarda — kullanılır. Alan sayısının değiştiği verilerde işe yaramaz.
cut hızlıdır ve yazımı kısadır, ama üç kesin sınırı vardır.
Ayırıcı tek karakterdir.
printf 'a::b::c\n' | cut -d'::' -f2
cut: bad delimiter
Alan tabanlı araç aynı işi düzenli ifadeli ayırıcıyla yapar:
printf 'a::b::c\n' | awk -F'::' '{ print $2 }'
b
Ardışık ayırıcılar birleştirilmez. Her ayırıcı yeni bir alan başlatır:
printf 'a b c\n' | cut -d' ' -f2 printf 'a b c\n' | awk '{ print $2 }'
b
cut ikinci alanı boş buldu, çünkü iki boşluk arasında boş bir alan var. Alan tabanlı
aracın öntanımlı ayırıcısı boşluk kümesi olduğu için b döndü. Hizalanmış ya da elle
yazılmış metinlerde bu fark belirleyicidir.
Alan sırası değiştirilemez. İstenen alan numaraları hangi sırayla yazılırsa yazılsın, çıktı dosyadaki sırayı izler:
head -1 erisim.log | cut -d' ' -f9,1
10.0.0.12 200
Sıra değiştirmek için alan tabanlı araç gerekir:
head -1 erisim.log | awk '{ print $9, $1 }'
200 10.0.0.12
Bu üç sınır, cut için net bir kullanım alanı bırakır: tek karakterle ayrılmış, ardışık
ayırıcı içermeyen ve alan sırası değişmeyecek veriler. Kütük dosyası bu tanıma uyduğu
için kursun ilk konularında kullanıldı.
Yan Yana Yapıştırma
paste, dosyaların karşılıklı satırlarını birleştirir. cut işleminin tersidir.
cut -d' ' -f7 erisim.log | head -3 > y.txt cut -d' ' -f9 erisim.log | head -3 > k.txt paste y.txt k.txt
/index.html 200 /statik/stil.css 200 /urun/12 200
Öntanımlı ayırıcı sekmedir; -d değiştirir:
paste -d: y.txt k.txt
/index.html:200 /statik/stil.css:200 /urun/12:200
-s seçeneği her dosyanın satırlarını tek satırda birleştirir; listeyi virgülle ayrılmış
metne çevirmenin kısa yoludur:
paste -sd, k.txt
200,200,200
paste, satırların konumsal olarak eşleştiğini varsayar. Bir dosyada satır eksikse
tüm hizalama kayar ve sonuç sessizce yanlış olur. Anahtar üzerinden eşleştirme
gerekiyorsa önceki dersteki join kullanılır; paste yalnızca sıraya güvenilebilen
verilerde uygundur.
Karakter Düzeyi Dönüştürme
tr, girdideki karakterleri tek tek eşler. Kalıp tanımaz, alan tanımaz, satır tanımaz —
yalnızca karakter kümeleri üzerinde çalışır ve yalnızca standart girdiden okur.
printf 'merhaba\n' | tr 'a-z' 'A-Z'
MERHABA
Üç seçenek en sık kullanılanlardır:
printf 'aaa bbb\n' | tr -s ' ' # ardisik yinelemeleri teke indir printf 'a1b2c3\n' | tr -d '0-9' # kumedeki karakterleri sil printf 'a1b2c3\n' | tr -cd '0-9' # kumenin disindakileri sil
aaa bbb abc 123
tr -s ' ' ile ardışık boşlukları teke indirmek, cut kullanılabilir hâle getirmenin
yaygın bir hazırlık adımıdır.
En sık kullanımı, ayırıcıyı satır sonuna çevirerek her alanı ayrı satıra dökmektir:
tr ' ' '\n' < erisim.log | grep -c '^"GET$'
27
tr, kalıp tabanlı araçlardan çok daha ucuzdur çünkü hiçbir şey ayrıştırmaz. Karakter
eşlemesi yeterliyse akış editörü çağırmaya gerek yoktur.
Dosyayı Parçalara Bölmek
split, büyük bir dosyayı sabit boyutlu ya da sabit satırlı parçalara ayırır.
mkdir -p parca split -l 10 erisim.log parca/kutuk- ls parca
kutuk-aa kutuk-ab kutuk-ac
wc -l parca/*
10 parca/kutuk-aa
10 parca/kutuk-ab
10 parca/kutuk-ac
30 total
-l N satır sayısına, -b N bayt sayısına göre böler. Sonek uzunluğu -a ile
ayarlanır; öntanımlı iki harf, 676 parçaya kadar yeterlidir.
İki kullanım alanı vardır. Birincisi, bellek sınırına sığmayan bir dosyayı parça parça işlemek. İkincisi, parçaları ayrı süreçlere dağıtarak koşut işlemek — parçalar bağımsız işlenebiliyorsa toplam süre parça sayısına bölünür.
Bayt sınırına göre bölmenin satırları ortadan kesebileceğine dikkat edilmelidir; satır
tabanlı veride -b yerine -l kullanılır.
Araç Seçimi
Bu konudaki altı ders, aynı veriye farklı açılardan bakan bir araç ailesi kurdu. Aralarındaki seçim ölçütü sorunun biçimidir:
| Soru | Araç |
|---|---|
| Hangi satırlar kalıba uyuyor | süzgeç (grep) |
| Satırın içindeki metni değiştir | akış editörü (sed) |
| Alanlarla hesap yap, anahtar başına birik | alan tabanlı araç (awk) |
| Sabit ayırıcılı veriden sütun al | cut |
| Sütunları birleştir | paste, join |
| Karakterleri eşle, sil, sıkıştır | tr |
| Sırala, tekilleştir, küme işlemi yap | sort, uniq, comm |
İki genel kural bu tablonun üzerinde durur.
En dar aracı seçin. Alan tabanlı araç, tablodaki işlerin hemen hepsini yapabilir; her
şeyi onunla yazmak yine de yanlıştır. Dar araç daha kısa yazılır, daha hızlı çalışır ve
okuyan kişiye niyeti anlatır. awk '/404/ { print }' yazımı, grep 404 ile aynı işi
yapar ama okuyucuya “burada bir hesap var mı” diye düşündürür.
Bir problemi üç araçtan fazlasıyla çözüyorsanız aracı değiştirin. Beş halkalı boru hatları yazılabilir ve bu kursta yazıldı; ama bir betikteki her hat böyleyse, işin kabuk sınırının ötesine geçtiği düşünülmelidir. Kabuk, süreçleri birbirine bağlamakta rakipsizdir; karmaşık veri yapıları ve çok adımlı iş mantığı için tasarlanmamıştır.
Betiğe Uygulama
Metin işleme konusunun sonunda rapor.sh, üç bölümünü de asıl araçlarıyla üretiyor:
ozet() { # ozet KUTUK
awk '
{ istek++; bayt += $10; sinif[substr($9, 1, 1)]++ }
END {
printf "istek : %d\n", istek
printf "bayt : %d\n", bayt
printf "ortalama: %.1f bayt\n", (istek ? bayt / istek : 0)
for (s = 2; s <= 5; s++)
printf " %sxx %4d %%%.1f\n", s, sinif[s], (istek ? sinif[s] * 100 / istek : 0)
}
' "$1"
}
en_cok_yol() { # en_cok_yol KUTUK ADET
cut -d' ' -f7 "$1" \
| sed -E 's#/[0-9]+#/:id#g' \
| sort | uniq -c | sort -k1,1nr -k2,2 | head -"$2"
}
hata_yollari() { # hata_yollari KUTUK
awk '$9 ~ /^[45]/ { n[$7]++ } END { for (y in n) printf "%3d %s\n", n[y], y }' "$1" \
| sort -k1,1nr -k2,2
}
Her fonksiyon tek bir soruyu yanıtlıyor, tek bir veri yolu izliyor ve çıktısı belirlenimci. Betiğin iskeleti ise hâlâ eksik: hata durumunda yarım rapor üretiyor, geçici dosya bırakıyor ve elle çalıştırılmayı bekliyor.
Özet
cuttek karakterli ayırıcı ister, ardışık ayırıcıları birleştirmez ve alan sırasını değiştiremez; bu üç sınır dışında en ucuz sütun aracıdır.pastedosyaları konumsal olarak yan yana getirir; anahtar eşleştirmesi gerekiyorsajoinkullanılır.trkarakter kümeleri üzerinde çalışır; kalıp tanımaz ve yalnızca standart girdiden okur.splitdosyayı satır ya da bayt sınırına göre parçalar; satır tabanlı veride-lkullanılır.- Araç seçiminde en dar araç yeğlenir; bir problem üç araçtan fazlasını gerektiriyorsa kabuk sınırının aşıldığı düşünülmelidir.
Sonraki Adım
Betik doğru çıktı üretiyor, ama yalnızca her şey yolunda gittiğinde. Bir komut başarısız olduğunda rapor yarım kalıyor ve çıkış kodu bunu bildirmiyor; tanımsız bir değişken sessizce boş dizgi olarak genişliyor. Sonraki konu bu boşlukları kapatır ve katı kip seçenekleriyle başlar: hangi hataların betiği durdurması gerektiğini, hangi seçeneğin bunu ne ölçüde sağladığını ve seçeneklerin kendi tuzaklarını ele alarak.
İlerlemeni kaydetmek ve not almak için Giriş yap
Notlarım
Not almak için giriş yapmalısın.