3

Oderskyの本「ProgramminginScala」の第2版、セクション5.7(89ページ)では、「==」演算子は次のように説明されています。

「ご覧のとおり、==は、ほとんどの場合に必要な等式比較が得られるように慎重に作成されています。これは、非常に単純なルールで実現されます。最初に左側でnullを確認し、nullでない場合は、 equalsメソッド...自動ヌルチェックがあるので、自分でチェックする必要はありません(7)」

次に、メモ「7」:

「自動チェックは右側を調べませんが、引数がnullの場合、適切なequalsメソッドはfalseを返す必要があります。」

nullチェックがRHSを調べない場合、null ==何かが常にfalseと評価されることを期待していました...しかし、試してみたところ、null==nullはtrueと評価されました。

この本はscala2.8に基づいています。ある時点で言語が変わったのでしょうか、それとも説明を理解していなかったのでしょうか。

私が使用したdroolsエンジンでは、==は、LHSがnullで、RHSがnullでない場合、RHSのequalsメソッドがLHSに渡されるように解釈されました。最も合理的なequalsメソッドはnullに対してfalseを返すはずですが、私はdroolsエンジンがこれを処理する方法が好きでした。SQLでは、null!=nullに慣れています。

4

2 に答える 2

2

この理由は==、 AnyRef でどのように実装されているかです。

final def ==(that: AnyRef): Boolean =
    if (this eq null) that eq null
    else this equals that

eqは、両方の変数が同じオブジェクトを参照しているかどうかをチェックするメソッドであるため、この場合、スニペットの 3 行目のnull == null両方のチェックで true が返されます。eq null

于 2012-09-28T11:37:15.750 に答える
2

引用されたテキストは、LHS が でない場合に何が起こるかを述べているだけのように思われるnullので、その部分に矛盾はありません。LHS の場合に何が起こるかについての説明は、null引用しなかったテキストの一部にあるか、完全に欠落している可能性があります。

注 (7) は、LHS が でない場合null、RHS でチェックが実行されず、RHS が単に に渡されることを説明していequalsます。したがって、 のようなものを比較する場合someExpression == null、Scala は最初に null でないかどうかをチェックsomeExpressionしてから を呼び出しますsomeExpression.equals(null)

term1 == term2Scala のものは Java のものに変換されて いると言えます。

(term1 != null) ? term1.equals(term2) : (term2 == null)

(これは Java スニペットであるため==、上記の行では Java の参照の等価性を意味することに注意してください。)

于 2012-09-28T11:38:53.737 に答える