Bash'te ayrı satırlara dizi öğeleri yazdırılsın mı?


229

Bash dizisinin dizi öğesini ayrı satırlara nasıl yazdırabilirim? Bu işe yarıyor, ama kesinlikle daha iyi bir yol var:

$ my_array=(one two three)
$ for i in ${my_array[@]}; do echo $i; done
one
two
three

Bunu denedim ama işe yaramadı:

$ IFS=$'\n' echo ${my_array[*]}
one two three

Yanıtlar:


437

Bunu yapmayı deneyin:

$ printf '%s\n' "${my_array[@]}"

Arasındaki fark $@ve $*:

  • Belirtilmemiş, sonuçlar belirtilmemiş. Bash'te her ikisi de ayrı ayrı argümanlara genişler, sonra da sözcük bölme ve globbed olur.

  • Belirtildi, "$@"her öğeyi ayrı bir bağımsız değişken olarak "$*" genişletirken, tek bir bağımsız değişkende birleştirilen bağımsız değişkenlere genişler: "$1c$2c..."( cilk karakter, burada IFS).

Neredeyse hep istiyorsun "$@". Aynı şey geçerli "${arr[@]}".

Her zaman teklif ver!


5
Ayrıca, iç boşluklu öğelerin yanlışlıkla ayrılmadığından emin olmak istiyorsanız, değişken başvurusunun etrafındaki çift tırnak işaretleri önemlidir.
danfuzz

4
@ sputnick: çalışmıyor, dizi öğeleri tek bir satıra çıkıyor
Axel Bregnsbo

1
Komuttan sonraki iki kısa çizgi ne için? Kılavuzda herhangi bir referans bulamadım.
joanpau

3
Dizide herhangi bir öğe yoksa, boş satır çıkmaması için bunu yapmanın bir yolu var mı | grep -v '^$'?
Noel Yap

2
@espaciomore '% s \ n' printf işlevinin çıktısının biçimidir. % s, bir dize bağımsız değişkeni (bu durumda dizi öğesi) için bir yer tutucu anlamına gelir ve \ n bundan sonra bir satır sonu ekler. Böylece, dizideki her öğe için çıktıda bir dize ve bir satır sonu olacaktır.
Koja

71

Sadece yankı argümanı alıntı:

( IFS=$'\n'; echo "${my_array[*]}" )

alt kabuk kullanımdan sonra IFS'nin geri yüklenmesine yardımcı olur


3
özür dilerim, sadece 'printf' işlevini öğrendiğim için çözümünüzü daha iyi sevmeme rağmen onay işaretimi sputnick'e taşıdım.
Axel Bregnsbo

3
Bu cevap için teşekkürler - Beğendim! Genişletmeden sonra çok kötü görevler oluyor, bu yüzden IFS=$'\n' echo "${my_array[*]}"çalışmıyor. Oh iyi!
cxw

@cxw, "ödevler olur" ile ne demek istiyorsun?
Steven Shaw

1
@bschlueter, Bash 4 ile denedim - 4.4.23 (1) -çalışma - ve işe yarıyor!
Steven Shaw

1
@cxw Ah, orada ne yapmaya çalıştığını görmedim. Bence işe yaramıyor çünkü echoBash'te yerleşik. Ancak, bir işleve sarın ve işe yarayacak! gist.github.com/steshaw/53ba0095bce8ccab52d26a14375dedb8
Steven Shaw

40

Kullanımı için :

for each in "${alpha[@]}"
do
  echo "$each"
done

Kullanımı tarihini ; değerleriniz şunları içeriyorsa bunun başarısız olacağını unutmayın !:

history -p "${alpha[@]}"

Basename kullanma ; değerleriniz şunları içeriyorsa bunun başarısız olacağını unutmayın /:

basename -a "${alpha[@]}"

Shuf kullanma ; sonuçların sırayla çıkmayabileceğini unutmayın:

shuf -e "${alpha[@]}"

19
"shuf" ... "sırayla çıkmayabilir" ... komik.
Walf

4
shuf için. Bunu kullanmayı kim düşünebilirdi?
fbicknel

3

Cevapları burada bir dev için denedim ... eğer döngü, ama herhangi bir sevinç almadım - bu yüzden böyle yaptım, belki dağınık ama iş yaptım:

 # EXP_LIST2 is iterated    
 # imagine a for loop
     EXP_LIST="List item"    
     EXP_LIST2="$EXP_LIST2 \n $EXP_LIST"
 done 
 echo -e $EXP_LIST2

Her ne kadar bu listeye bir boşluk ekledi, ki bu iyi - biraz girintili istedim. Ayrıca "\ n" orijinal $ EP_LIST içinde basılabileceğini varsayın.


5
Tam bir örnek gibi görünmüyor.
kenorb

3

Bir başka yararlı varyant, aşağıdakilere yönelik borudur tr:

echo "${my_array[@]}" | tr ' ' '\n'

Bu basit ve kompakt görünüyor


11
Bu molalar hariçmy_array=( "one two" three )
Mike Holt

Çift tırnak işareti ile düzeltildi.
Steven Shaw

Bash sürüm 4+ reklamı olarak işe yaramadı , kullanmak zorunda kaldı echo "${my_array[@]}" | tr '' ' \n', ancak kişisel olarak echoböyle kullanmaktan kaçınmak istiyorum, trbenim seçimim gibi tr '' ' \n' <<<"${my_array[@]}"bir şey daha sonra okumak için biraz daha kolay olabilir düşünüyorum .
S0AndS0
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.