Null / Equals

概要

適切に NullEquals のチェックを行っている際に獲得できる実績です. これらのチェックを適切に行わないと,プログラムの処理が停止してしまったり,想定外の動作をしてしまう原因になります.

タイトル
Nail in the bran

この実績には,以下の5つのルールが含まれます:

  • BrokenNullCheck
  • CompareObjectsWithEquals
  • EqualsNull
  • MisplacedNullCheck
  • UseEqualsToCompareStrings

BrokenNullCheck

||&& の書き間違いをすると,正しく null チェックできません. この際, 'NullPointerException' がスローされます.

コード例

public String bar(String string) {
  // !!! 正しくは `&&` です
  if (string!=null || !string.equals(""))
      return string;

  // !!! 正しくは `||` です
  if (string==null && string.equals(""))
      return string;
}

このルールのチェックには,PMDの BrokenNullCheck を用いています.

CompareObjectsWithEquals

オブジェクトの比較には == 演算子や != 演算子ではなく, equals メソッドを使うのが適切です.

コード例

class Foo {
  boolean bar(String a, String b) {
    return a == b;  // !!! `return a.equals(b);` がより適切です
  }
}

このルールのチェックには,PMDの CompareObjectsWithEquals を用いています.

EqualsNull

null のチェックには equals メソッドではなく, == 演算子や != 演算子を使うのが適切です.

コード例

String x = "foo";

if (x.equals(null)) {   // !!! 下の書き方がより適切です
  doSomething();
}

if (x == null) {
  doSomething();
}

このルールのチェックには,PMDの EqualsNull を用いています.

UseEqualsToCompareStrings

文字列の比較には == 演算子や != 演算子ではなく, equals() メソッドを使うのが適切です.

コード例

public boolean test(String s) {
  if (s == "one") return true;        // !!! 下の書き方がより適切です
  if ("two".equals(s)) return true;
  return false;
}

このルールのチェックには,PMDの UseEqualsToCompareStrings を用いています.

注意

CompareObjectsWithEqualsEqualsNullUseEqualsToCompareStrings を混同しないように注意してください. String 等のオブジェクトの比較には equals メソッドが, null や文字列のチェックには == 演算子や != 演算子が適しています.

MisplacedNullCheck

null チェックの位置が正しくないと,以下の問題が起こります:

  1. 変数が null の場合, NullPointerException が常にスローされます.
  2. 変数が null にならない場合,不必要なコードになります.

コード例

public class Foo {
  void bar() {
    // !!! a が null の場合,`a.equals(baz)`の部分で NullPointerException がスローされます
    // 正しくは `a != null && a.equals(baz)` です(一番目に該当)
    if (a.equals(baz) && a != null) {
      doSomething();
    }
  }
}

public class Foo {
  void bar() {
    // !!! a が nullでない場合,`a.equals(baz)`の部分で判定が終わるため `a == null` は不必要です
    // 正しくは `a == null || a.equals(baz)` です(二番目に該当)
    if (a.equals(baz) || a == null) {
      doSomething();
    }
  }
}

このルールのチェックには,PMDの MisplacedNullCheck を用いています.