7

一部の会社のプロジェクトコードでは、次のようなものをよく読んでいます。

boolean foo = Boolean.FALSE;

AFAIKはJavaでローカル変数を初期化するだけでよく(Pascalのようにランダムな値はありません)、特にブール値の場合は初期化が必要になることが多いという事実に加えて、ここで何を見逃しますか?なぜだめですか:

boolean foo = false;

理解できません。また、PMDやFindbugsなどのコード分析ツールもそれをマークしています。しかし、なぜ?

編集:バイトコードがそこにあることを除いて、実際にはあまり知らずに、サンプルクラスを作成して逆コンパイルしました。Boolean.FALSEは次の場所に移動しました:

0: getstatic #15 // Field java/lang/Boolean.FALSE:Ljava/lang/Boolean; 
3: invokevirtual #21 // Method java/lang/Boolean.booleanValue:()Z 
6: istore_1 

'false'バリアントは次のようになりました:

0: iconst_1 
1: istore_1 

したがって、これについてあまり知らなくても、ステートメントが多いほど実行に時間がかかるため、間違っているだけでなく、長期的には遅くなると思います。

4

5 に答える 5

12
boolean foo = Boolean.FALSE;

これは奇妙で不必要に複雑なコードであり、Javaをあまりよく知らない人によって書かれたものです。このようなコードを書くべきではありません。PMDとFindBugsはこれをマークする権利があります。

Boolean.FALSE自動ボックス解除されるjava.lang.Booleanオブジェクトです。コンパイラは基本的にこれを次のように変換します。

boolean foo = Boolean.FALSE.booleanValue();

Javaで変数を初期化する必要はまったくありません...

メンバー変数は明示的に初期化する必要はありません。そうしないと、デフォルト値(falseの場合boolean)で初期化されます。ローカル変数は明示的に初期化する必要があります。ローカル変数を初期化せずに使用しようとすると、コンパイラーはエラーを出します。

于 2012-10-18T12:47:05.923 に答える
3

どちらも同じです。しかし、boolean foo = false;それで十分です。

于 2012-10-18T12:44:17.327 に答える
2

実際、自動ボックス解除Booleanされた定数を使用するスタイルは、多くのJavaプロジェクトに特有の全体的な過度の冗長性とうまく調和しています。例えば:

public boolean isItOrIsItNotTheValueWeExpect(String aStringParameterThatCouldBeNull) {
  boolean booleanReturnValue = Boolean.FALSE;
  if (aStringParameterThatCouldBeNull != null) {
    if (aStringParameterThatCouldBeNull.length() > 3) {
      booleanReturnValue = Boolean.TRUE;
    }
    else {
      booleanReturnValue = Boolean.FALSE;
    }
  }
  else if (aStringParameterThatCouldBeNull == null) {
    booleanReturnValue = Boolean.TRUE.booleanValue();
  }
  return booleanReturnValue;
}

明らかに、上記のコードは、この読み取り不可能な混乱よりもはるかに好まれます。

public boolean validate(String s) {
  return s == null? true : s.length() > 3;
}

三項演算子の発生そのものが違反と見なされ、一部のプロジェクトではCheckStyleによってフラグが付けられています。

プロジェクトがこれらのようなスタイルのガイドラインに準拠している場合、それは疑わしいコード行を正当化する可能性があります。

于 2012-10-18T12:44:36.270 に答える
2

これを行う正当な理由はありません。おそらく初心者のJavaプログラマーでした。あまり心配する必要はありません。falseに置き換えてください。

同時に、通常は、常にではないにしても、最終的な値を持たない変数を宣言しないようにコードを配置できます。つまり、オブジェクトを不変にして、オブジェクトを考えやすくすることができます。xの値は何ですか?foo()とbar()の呼び出しの間のxの値は何ですか?最初の方が一般的に答えやすいです。これには、慣れていない可能性のある行に沿ってクラスを分割する必要がありますが、少なくとも試してみることをお勧めします。

于 2012-10-18T12:46:21.057 に答える
1

最初の方法は1.4以前のJVMでは機能しませんが、実際には違いはありません。1つ目は、ブールオブジェクトから静的な値をフェッチし、オートボクシング(1.5で導入)に依存してブールオブジェクトからブールプリミティブに変更するため、より複雑になりますが、速度が上がるとは想像できません。違い。

一般に、変数の特定の初期値を想定している場合は、コードを読みやすくするために宣言するのではなく、初期化することをお勧めします。

于 2012-10-18T12:37:43.517 に答える