- ベストアンサー
Javaのコンストラクタはキャスト時にも実行されるのか?
- Javaのコンストラクタはインスタンス化した際に実行されますが、キャスト時にも実行されます。
- 上記のコードでは、21行目のCarクラスへのキャスト処理時にVehicleのコンストラクタが実行されるため、変数makeには初期値の"Lexus"がセットされます。
- Javaの仕様書にキャスト時のコンストラクタの実行に関する明確な記述はありませんが、オブジェクトの型が変わる際にはキャスト先のコンストラクタが実行されるという動作が一般的です。
- みんなの回答 (2)
- 専門家の回答
質問者が選んだベストアンサー
中々面白い問題を解いていらっしゃいますね。Javaで直列化を扱う場合、誰もが一度は通る道です。今回のソースですと、10-13行目で対象オブジェクトの直列化(Serialize)、19-22行目で直列化の復元(deserialize)を行っています。 直列化を行う場合、以下の要件を満たすことが必要です(かなり簡略化して書いてます)。 1. 対象オブジェクトのクラスがjava.io.Serializableインターフェースを実装していること (java.io.Serializableインターフェースを実装することにより「直列化可能なクラス」になります) 2. 対象オブジェクトが保持するフィールドのクラスも、java.io.Serializableインターフェースを実装していること 3. 親クラスが直列化不可能なクラスであってもサブクラスが直列化可能なクラスであれば、直列化は可能。但し、親クラスのデフォルト・コンストラクタが外部から呼び出せること。 今回の場合は、「3」が当てはまりますね。(Vehicleクラスは直列化不可能、その子供であるCarクラスは直列化可能なクラスになります。)で、この「3」の場合なのですが、復元時にちょっと困った(?)動きをします。それは、復元時に親クラスのデフォルト・コンストラクタを呼ぶという動作をするのです。よって、親クラスで保持しているフィールドは親クラスの定義にて初期化されます。ですので、フィールドcolorとmakeは親クラスの定義に紐付く値で、weightは直列化されたCarクラスの値そのままで復元されます。 質問主様は、「キャスト時にコンストラクタが実行される」と思われているようですが、実際は上記のように直列化から復元する時に行っているのです。ちなみに、Vehicleクラスもjava.io.Serializableインターフェースを実装している場合は、上記処理は行われず直列化時そのままの状態で復元されます。 この辺りの情報ですが、Java SE APIのjava.io.Serializableインターフェースの項をご参照ください。非常に判りづらい書き方をしていますが、上記のようなことが記載されています。 以上、ご参考になりましたら。
その他の回答 (1)
- himajin100000
- ベストアンサー率54% (1660/3060)
http://docs.oracle.com/javase/7/docs/api/java/io/Serializable.html >To allow subtypes of non-serializable classes to be serialized, the subtype may assume responsibility for saving and restoring the state of the supertype's public, protected, and (if accessible) package fields. The subtype may assume this responsibility only if the class it extends has an accessible no-arg constructor to initialize the class's state. It is an error to declare a class Serializable if this is not the case. The error will be detected at runtime. >During deserialization, the fields of non-serializable classes will be initialized using the public or protected no-arg constructor of the class. A no-arg constructor must be accessible to the subclass that is serializable. The fields of serializable subclasses will be restored from the stream.
お礼
takepan_toki様 ご丁寧な解説ありがとうございます。 キャスト時にコンストラクタが実行されているのではなく、親クラスがSerializableインターフェースを実装していない場合、デシリアライズの際に親のデフォルトコンストラクタが動いているのですね。 とても参考になりました。 ありがとうございました。