Yang lebih idiomatis dalam skrip bash: `|| true` atau `|| : `?

36

Saya tidak terlalu banyak membuat skrip shell, jadi saya sedikit terkejut ketika saya membaca dokumentasi untukgit submodule dan saya melihat sintaks yang mereka gunakan dalam dokumentasi ini:

Pengembalian yang tidak nol dari perintah dalam submodule apa pun menyebabkan pemrosesan berakhir. Ini bisa diganti dengan menambahkan || :ke akhir perintah.

Saya harus mencari yang || :merupakan singkatan untuk memaksa perintah untuk keluar dengan sukses. Kapan saja saya harus membuat perintah keluar dengan sukses, saya menggunakan || true. Apakah || :dianggap lebih idiomatis?

Mark Rushakoff
sumber
Perlu dicatat bahwa ||:(tanpa ruang) juga berlaku di bash. Itu melakukan hal yang sama dengan || :atau || true.
Bruno Bronosky

Jawaban:

38

truetidak dibangun ke dalam shell Bourne. :selalu (itu adalah cara untuk memasukkan komentar sebelum #diperkenalkan).

Itu, dan karena itu lebih pendek untuk jenis mungkin adalah alasan utama orang memilih :lebih true.

Perhatikan perbedaan lain dalam shell POSIX (untuk bash, hanya dalam mode POSIX): sementara truebuiltin biasa (bahkan tidak harus builtin), :adalah builtin khusus . Itu memiliki beberapa implikasi, yang sebagian besar tidak mungkin berdampak pada kasus khusus ini:

  • Jika suatu :perintah gagal, termasuk karena pengalihan yang gagal, itu menyebabkan shell keluar. Dalam praktiknya, itu mungkin tidak akan membuat perbedaan kecuali Anda meneruskan pengalihan:

    $ sh -c ': > /   ; echo HERE'
    sh: 1: cannot create /: Is a directory
    $ sh -c 'true > /; echo HERE'
    sh: 1: cannot create /: Is a directory
    HERE
    
  • di var=value :, vartetap disetel ke valuesetelah :pengembalian, bukan dalam kasus true:

    $ var=1; var=2 :   ; echo "$var"
    2
    $ var=1; var=2 true; echo "$var"
    1
    

Juga mencatat bahwa || truekarya-karya di kerang dari rcdan cshkeluarga tetapi tidak || :(tapi tidak untuk membatalkan set -edi csh).

|| :tidak sama dengan :. Ini berarti atau menjalankan :sebaliknya (yaitu, jika pipa sebelumnya gagal).

set -e
false

Akan menyebabkan shell keluar karena set -edan falsememiliki status keluar yang tidak nol (gagal). The set -eefek dibatalkan jika perintah yang kembali status exit non-nol digunakan sebagai kondisi seperti di:

if false; then ...
while false; do ...
false && : ...
false || : ...

false && :hanya membatalkan set -e. false || :membatalkan set -edan mengatur status keluar menjadi 0lebih idiomatis untuk mengatakan bahwa kami ingin mengabaikan kode keluar kegagalan perintah. Sebagian besar akan berpendapat bahwa || trueitu lebih terbaca (menyampaikan niat lebih jelas).

Stéphane Chazelas
sumber
5
&& :brilian, apakah ada dokumen atau bacaan lebih lanjut tentang ini? Google gagal pada saya mencoba menemukan kata kunci semacam ini ...
Ian Bytchek
5

Secara umum, dalam bash, titik dua :dan truesetara.

Apakah || : dianggap lebih idiomatis?

Saya pikir ini didasarkan pada konteksnya .

Jika Anda ingin return value, atau conditionselalu benar, Anda harus menggunakan truekata kunci, itu akan membuat kode Anda lebih jelas dan membiarkan pemirsa tahu bahwa Anda ingin menekankan nilai yang benar , yaitu:

while true; do something

atau

<commnad>
RETURN_VALUE= $? || true

Dan jika Anda tidak ingin melakukan apa pun , atau NOPmenggunakan shell, Anda harus menggunakan titik dua:

if condition
then
    : # DO NOTHING HERE
else
    do something
fi 

atau

while conditon
do
    : # DO NOTHING HERE
done
cuonglm
sumber
5

Sebagian besar respons ini gagal mengatasi penggunaan paling umum dari :.

Pertama, diskusi ini tidak terkait dengan shell yang bukan turunan shell Bourne ( sh). Yang mengatakan, semua cangkang turunan Bourne melihat truedan :sebagai hal yang sama. Programmer dulunya didorong untuk menggunakan :daripada true, karena :selalu built-in sementara dulu ada kasus di mana truetidak selalu built-in.

:memiliki dua kegunaan. Ini bukan sinonim untuk #, tetapi memiliki fungsi yang berbeda. Saat debugging skrip Anda di bawah a set -x, baris tempat #digunakan dijatuhkan oleh parser dan benar-benar diabaikan, sedangkan baris dengan :diuraikan dan dievaluasi. Ini sangat berguna dalam debugging karena di bawah -xbaris tersebut ditampilkan dan nilainya setelah evaluasi ditampilkan. Ini seperti menempatkan printpernyataan dalam kode Anda yang hanya ditampilkan dalam -xmode. Hati-hati dengan nilai setelahnya :karena itu adalah kode asli dan efek sampingnya dapat memengaruhi program Anda.

cdr
sumber
1
Apa penggunaan kedua?
Peter Mortensen