本節では、複雑な条件を表現するために if や cond と組み合わせてよく用いられる構文について解説します。また、and や or
といった構文も、複数条件構文の一種として単独で使用することが可能です。
この関数は condition が偽であるかどうかを判定します。condition が nil であれば t を、そうでなければ nil を返します。関数 not は null と同一であり、空のリストや nil の値を判定する場合は、null
という名前を使用することを推奨します。
and 特殊形式は、すべての conditions
が真であるかどうかを判定します。これは、conditions
を記述された順に一つずつ評価することで動作します。
conditions のいずれかが nil
と評価される場合、残りの conditions に関わらず and の結果は nil
でなければなりません。したがって、and は残りの conditions を無視して、直ちに nil を返します。
すべての conditions が nil
以外となった場合、最後の一つの値が and 形式の値となります。conditions がなく (and) だけの場合は
t が返されますが、これはすべての conditions が nil
以外となったため妥当です。(考えてみてください。どれがそうではなかったでしょうか?)
以下に例を示します。最初の条件は整数 1 を返しますが、これは nil
ではありません。同様に、2番目の条件は整数 2 を返しますが、これも nil
ではありません。3番目の条件は nil であるため、残りの条件が評価されることはありません。
(and (print 1) (print 2) nil (print 3))
⊣ 1
⊣ 2
⇒ nil
and を使用した、より現実的な例を以下に示します。
(if (and (consp foo) (eq (car foo) 'x))
(message "foo is a list starting with x"))
なお、(consp foo) が nil
を返す場合は (car foo) は実行されないため、エラーを回避できます。
and 式は、if または cond のいずれかを使って記述することもできます。方法は以下の通りです。
(and arg1 arg2 arg3) ≡ (if arg1 (if arg2 arg3)) ≡ (cond (arg1 (cond (arg2 arg3))))
or 特殊形式は、conditions
のうち少なくとも1つが真であるかどうかを判定します。これは、すべての conditions
を記述された順に一つずつ評価することで動作します。
conditions のいずれかが nil
以外の値と評価された場合、or の結果は nil
以外である必要があります。そのため、or は残りの conditions を無視して直ちに戻ります。返される値は、直前に評価された条件の nil 以外の値となります。
すべての conditions が nil
となった場合、or 式は nil
を返します。conditions がなく (or)
だけが nil を返すのは、すべての conditions が nil
となったため妥当です。(考えてみてください。どれがそうではありませんでしたか?)
例えば、この式は x が nil または整数の
0 であるかどうかを判定します:
(or (eq x nil) (eq x 0))
and 構文と同様に、or は cond を用いて記述できます。例えば:
(or arg1 arg2 arg3)
≡
(cond (arg1)
(arg2)
(arg3))
orをifを用いて書き表すこともできそうですが、完全にはそうはいきません:
(if arg1 arg1
(if arg2 arg2
arg3))
これは arg1 や arg2
を2回評価する可能性があるため、完全には等価ではありません。対照的に、(or arg1 arg2 arg3) はいかなる引数も2回以上評価することはありません。
この関数は、condition1 と condition2
のブール値による排他的論理和を返します。つまり、両方の引数が nil であるか、あるいは両方が
nil 以外である場合、xor は nil を返します。それ以外の場合は、nil
以外である方の引数の値を返します。
なお、or とは異なり、両方の引数は常に評価される点に注意してください。