Ini adalah tindak lanjut dari komentar pada jawaban ini . Bit kode berikut tampaknya setara:
(and a b)
(when a b)
Tentu saja and
memungkinkan Anda menempatkan lebih banyak kondisi: (and a b c d)
berarti(when (and a b c) d)
Saya cenderung menggunakan when
hanya untuk mengekspresikan percabangan. Apakah ada perbedaan nyata? Apakah lebih baik menggunakan yang satu atau yang lain?
Saya tidak memiliki sumber C Emacs 'di tangan; and
adalah fungsi C; when
adalah makro yang berkembang if
, yang itu sendiri adalah fungsi C.
elisp
elisp-macros
conditionals
Sejuk
sumber
sumber
Jawaban:
TL; DR:
when
adalah tentang efek samping,and
adalah untuk ekspresi boolean murni.Seperti yang telah Anda perhatikan,
and
danwhen
hanya berbeda dalam sintaksis, tetapi sebaliknya sepenuhnya sama.Perbedaan sintaksis cukup penting, meskipun:
when
membungkus implisit diprogn
sekitar semua kecuali bentuk argumen pertama.progn
adalah fitur yang secara inheren penting: Ini mengevaluasi semua kecuali bentuk tubuh terakhir untuk efek sampingnya saja, membuang nilai apa pun yang mereka kembalikan.Dengan demikian,
when
adalah bentuk imperatif juga: Tujuan utamanya adalah untuk membungkus bentuk efek samping, karena hanya nilai bentuk terakhir yang paling penting bagi tubuh.and
di sisi lain adalah fungsi murni, yang tujuan utamanya adalah untuk melihat nilai kembali dari bentuk argumen yang diberikan: Kecuali jika Anda secara eksplisit membungkusprogn
argumennya, nilai setiap bentuk argumen adalah penting, dan tidak ada nilai yang pernah diabaikan .Oleh karena itu, perbedaan nyata antara
and
danwhen
gaya: Anda gunakanand
untuk ekspresi boolean murni, danwhen
untuk menjaga di sekitar bentuk efek samping.Karenanya, ini adalah gaya yang buruk:
Dan ini bagus:
Saya tahu bahwa beberapa orang tidak setuju tentang hal ini, dan dengan senang hati menggunakannya
and
untuk menjaga efek samping, tetapi saya pikir ini adalah gaya yang benar-benar buruk. Kami memiliki berbagai bentuk ini karena suatu alasan: Sintaks penting . Jika tidak, kita semua hanya akan menggunakanif
, yang merupakan satu-satunya bentuk kondisional yang Anda butuhkan di Emacs Lisp secara semantik. Semua bentuk boolean dan kondisional lainnya dapat ditulis dalam bentukif
.sumber
and
adalah tentang peduli tentang nilai kembali . Ini belum tentu bukan tentang menggunakan efek samping. Jika program saya peduli dengan nilai pengembalian maka saya gunakanand
. Jika tidak maka saya gunakanwhen
. TKI, saya gunakanwhen
hanya untuk efek samping, tapi saya mungkin akan menggunakanprogn
salah satu argumen untuk ituand
. Ini tentang apakah nilai pengembalian itu penting, bukan tentang apakah itu sendiri yang penting.and
bukan fungsi dalam Lisp yang saya tahu. Dalam Emacs Lisp itu adalah bentuk khusus, dalam Common Lisp itu adalah makro, hanya karena itu diharapkan memiliki perilaku hubung singkat (tidak mungkin untuk dicapai dengan fungsi, karena mereka selalu mengevaluasi argumen mereka).and
adalah fungsi, padahal sebenarnya tidak. Tidak masalah seberapa relevan fakta itu dengan pertanyaan, kita harus selalu menggunakan istilah yang benar, itu saja.nil
berarti semua "false", "the blank list", "void", dll. Misalnya dalam Skema dan Raket, hasil tidak jujur dariwhen
adalahvoid
(yaitu "tidak ada artinya") sedangkan untukand
itu adalah#f
("salah"). Meskipun ini N / A untuk Elisp, itu sesuatu yang mungkin dipertimbangkan oleh generalis Lisp.Biarkan saya memulai dengan mengatakan itu
(and a b)
dan(when a b)
dalam contoh Anda melakukan hal yang sama: Pertamaa
dievaluasi.b
dievaluasi jikaa
ini benar # .Tetapi
and
danwhen
digunakan untuk hal-hal yang berbeda.Anda akan menggunakan
(and a b)
untuk kembali benar # jika KEDUAa
danb
yang benar # (atau non-nil); dannil
sebaliknya.Anda akan menggunakan
(when a b)
atau lebih tepatnya,bila Anda ingin "b" kode untuk mengeksekusi jika dan hanya jika
a
adalah benar # .Berikut adalah contoh tempat Anda menggunakan
when
danand
bersama - sama:Di atas, fungsi
do-c
disebut hanya jika KEDUAa
danb
yang benar # .Referensi untuk belajar
when
bagian di sini)and
bagian di sini)# Semua referensi ke true merujuk ke Boolean TRUE.
sumber
and
tidak kembalit
jika semua argumennya bukan nol, tetapi nilai argumen terakhir.t
, saya berarti Boolean TRUE atau non-nihil. Terima kasih, saya akan menjelaskannya dalam jawaban saya.(when (and a b) c)
). Selain itu, bagian tentang bagaimanaand
danwhen
menyarankan bahwa itulah sebenarnya cara mereka digunakan secara umum, tetapi dasar dari pertanyaan ini adalah kenyataan bahwa saya sering melihat mereka digunakan secara berbeda (lihat misalnya jawaban yang saya tautkan dalam pertanyaan saya).