• ベストアンサー

ローカル変数の初期化方法の違い

以下の例1と例2は、何か違いがあるのでしょうか? 違うとすれば、どういう時にどちらの例を使用すべきなのでしょうか? ==== 例1 ==== public class TestClass {  private String text = "aaa";  // ... } ==== 例2 ==== public class TestClass {  private String text;  public TestClass() {   text = "aaa";  }  // ... }

質問者が選んだベストアンサー

  • ベストアンサー
  • thamansa
  • ベストアンサー率40% (95/232)
回答No.4

すみません、揚げ足をとるつもりはないのですが、 「そうだったっけ?」と思い、確かめてみました。 明示的にsuper();を書いても書かなくても、親クラスのコンストラクタは実行されるようです。 次のコードでは、abcと表示されました。 public class Parent {   String str;     public Parent(){       str = "abc";   } } public class Child extends Parent {   Child(){   }   public static void main(String[] args) {     Child c = new Child();     System.out.println(c.str);   } }

その他の回答 (4)

  • HarukaV49
  • ベストアンサー率53% (48/89)
回答No.5

#3です。 すみません、今見てびっくりしました(^^; 何の確認もしていない状態での書き込みで、ここを 汚して申し訳ありませんが、大嘘を書いていたとしたら まことに申し訳ありませんでした。

  • HarukaV49
  • ベストアンサー率53% (48/89)
回答No.3

TestClassを継承したときの動作が異なります。 public class SubTestClass extends TestClass |   public SubTestClass() {     // ここに super() がないとき     ...   }   ... } この場合、このサブクラスからTestClassのtext変数にアクセスする 直接的、間接的を問わず方法(メソッド)があったとき、 例1では、"aaa"になりますし、例2では""です。 >違うとすれば、どういう時にどちらの例を使用すべきなのでしょうか? この点を考慮して使い分けます。 継承して、コンストラクタを独自に実装した場合、textが"aaa"に 初期化されてはいけない場合は、例2の方法に限ります。 サブクラスでも常にtextが"aaa"の初期化されている必要があるならば、 例2のコードに加えて独自のコンストラクタ内でsuper()を呼ぶよう 注釈を行えは例1と動作上は一致しますが、この場合には明らかに 例1の方法が優っているでしょう。

pe_daichan
質問者

お礼

確かに! 継承すると動作が代わりますね。納得いたしました。

  • thamansa
  • ベストアンサー率40% (95/232)
回答No.2

コンストラクタのオーバーロードがあるときに、ソースコードのメンテナンス性などに違いが出てきます。 class Foo{   private String text;   public Foo(){     text = "aaa";   }   public Foo(int num){     text = "aaa";   } } 同じ値で初期化するコードが複数存在しているのは、一般に悪い実装とされます。 修正案1 class Foo{   private String text = "aaa";   public Foo(){   }   public Foo(int num){   } } 修正案2 class Foo{   private String text;   public Foo(){     text = "aaa";   }   public Foo(int num){     this();   } } 案1と案2を単純に見比べると1のほうがすっきりしていますが、実際のクラスではnumの初期化があったり、textの初期値もコンストラクタで受け取る場合があったりするので、その結果 this() を使うほうが最適だったりします。

pe_daichan
質問者

お礼

ご回答ありがとうございます。 そういえばオーバーロードがある時も、扱いが変わってきますね。納得です。

  • hrm_mmm
  • ベストアンサー率63% (292/459)
回答No.1

違いは、例1では、コンパイル時に確定、例2では、実行時に確定 というところでしょうか? この例では、動作的にどちらでもあまり変わらないと思うけど、 実行速度等については、識者の意見を待ちましょう。 私の場合、final にしたい時は、例1の宣言時にデータも入れる。 public class TestClass {  private final String text = "aaa"; 実行時に初期値も異なる物にしたい時は、例2のように public class TestClass {  private String text;  public TestClass( String x) {   text = x;  } といった使い分けをしてますけど。 あとは、「宣言時に必要なデータを先に代入してしまえば、初期化し忘れのエラーが減る」 というところかな。

関連するQ&A