2012-01-31 8 views
2

私はこのようなクラスがあります。Java - 親クラスコンストラクタを呼び出すことなくクラスをオーバーライドできますか?

public class BaseClass 
{ 
    public BaseClass(URL url, String something, String whatever) 
    { 
    // Do some stuff with URL, something and whatever 
    } 

    public List ImportantFunction() 
    { 
    // Some important stuff here 
    } 
} 

を私は、しかし、私は、コンストラクタで別のものをしたい、このクラスを使用します。コンストラクタが私にそれらを別々に行うために必要なこと。しかし、私は他のクラスメソッドのすべての機能を使いたいと思っています。

私は、クラスを拡張するのが最も簡単だと考えました。私はこれを行うときただし、コンストラクタは親のコンストラクタを呼び出すために私を必要とします。

super(url, something, whatever); 

は、それが基本クラスを拡張しますが、完全に異なるコンストラクタを持つことは可能ですか?私はあなたがスーパークラスのコンストラクタを呼び出す必要があります...

答えて

8

をまったく呼び出されるBaseClassコンストラクタを望んでいません。明示的に呼び出さないと、Javaは引数のないコンストラクタを自動的に呼び出そうとします。そのようなものがなければ、コンパイルエラーが発生します。呼び出すコンストラクタは、サブクラスのコンストラクタに渡される引数に対応する必要はありません。

これは必須です - オブジェクトのメンバ変数はコンストラクタで初期化でき、そのうちの1つを呼び出すとスーパークラスの内部的な仮定に違反する可能性があります。

この短いJNIを使​​用してJVMを中断する方法はありません。

+1

これで、カスタマイズしたいクラスがあるとします。そして、このクラスはどこかのオンラインから来ていると言うことができます。明らかに、元のコードを編集するだけでそれをカスタマイズするのは悪い考えです。その代わりに、クラスを拡張してカスタマイズを行います。そうすれば、クラスの新しいバージョンがオンラインでリリースされると、コード内のすべての変更をもう一度やり直す必要はありません。カスタムクラスを拡張するだけです。あなたが言っていることは、クラスをカスタマイズしたい場合、それらは親クラスのコンストラクタを呼び出すために強制されるということです。 –

+1

@Jakobudクラスが 'final'の場合、それをサブクラス化することはできません。呼び出したいコンストラクタがない場合は使用できません。これがJavaの仕組みです。Pythonのようなものではありませんが、修正プログラムを猿で修正することはできません。 – Borealid

+0

@ JakeWilson ...デフォルトのコンストラクタを 'private'にすることができます。この場合、使用できないことが保証されます。しかし、@Borealidが言うように、あなたは** _ A_コンストラクタ**を呼び出さなければなりません。 – will

2

あなたは、基本クラスのコンストラクタを呼び出します。あなたは、この特定のコンストラクタを呼び出したいいけない場合、あなたが拡張するとき次に、このコンストラクタは、最初にデフォルトで呼び出されます

public BaseClass(){ } 

デフォルトコンストラクタを定義する必要があります。それだけであなたのSubClassのコンストラクタが呼び出されます。

+1

最終的に、私は 'BaseClass'のコードをいずれかの方法で変更するつもりですか?このクラスは私のコードではありません。私は実際のコード自体を変更せずにカスタマイズしようとしています。私はちょうどコードを変更するかもしれないと言っていますか? –

+0

BaseClassを拡張する必要がある場合は、既に定義されているコンストラクタを呼び出すか、新しいデフォルトのものを定義する必要があります。残念ながら、他の方法はありません。 – sethu

+0

'BaseClass'は空のデフォルトコンストラクタを持たないため、書かれていないとお考えですか?それがあれば、それを拡張して空のコンストラクタを実行させ、何もしないことを知ることができるからです。 –

0

あなたは、その特定のコンストラクタをparent内で呼び出す必要はありません。親にデフォルトのコンストラクタが定義されている場合は、次のようにします。

public class ChildClass extends BaseClass { 
    public ChildClass(URL url, String something, String whatever) { 
     // implicit call to the Parent's default constructor if next line is commented 
     super(); // explicit call to the default constructor of ParentClass 

     // now do stuff totally specific to your ChildClass here 
    } 
} 
+1

親クラスにデフォルトのコンストラクタがある場合、super()の呼び出しは暗黙のため必須ではありません。 – Jeshurun

+1

必ずしも必要ではありませんが、コードではParentClassのデフォルトのコンストラクタへの暗黙的または明示的な呼び出しを行うことができるという点でその事実を強調したかっただけです。 – anubhava

0

スーパークラスのコンストラクタを編集しないでください。あなたは、これは既存のコードに影響を与えるかもしれないと心配している場合、私は通常、それをお勧めしませんが、しかし、あなたは、次の操作を行い使用することができます。

  1. 移動BaseClassの中に保護されたメソッドへのすべてのコンストラクタのコードを、のようなものを言います protected void init(URL url, String something, String whatever){\\constructor code}
  2. コールコンストラクタからこの方法

    公共BaseClassの(URLのURL、文字列何か、文字列の何でも){ のinit(URLのURL、文字列何か、文字列の何でも)。 }

  3. この保護されたメソッドをサブクラスでオーバーライドします。

+0

私はJavaにちょっと新しいですが、クラスをコンストラクタと呼ぶことなくクラスを拡張することはできません。クラスを拡張する全体のポイントは、基本クラスの機能を追加したり変更したりできることです。しかし、基本コンストラクタを呼び出す必要がある場合は、ポイントは何ですか? –

+0

@ Jakobud:コンストラクタ呼び出し中にオブジェクトの状態が矛盾し、予期しない動作が発生する可能性があるためです。説明については、[this](http://stackoverflow.com/a/3404369/473637)の回答を参照してください。 – Jeshurun

関連する問題