2011-11-22 8 views
5

ここで何が起こっているのか説明できる人はいますか?スーパークラス参照のJavaキャスト

CarおよびBikeは、サブタイプがVehicleであるとします。

Vehicle v参照は、Bikeにキャストされるようです。コンパイラが... Car cannot be cast to Bikeを吐き出すのは間違いだと私は知っています。

Vehicleは、Bikeにキャストできません。結局、Vehicle vVehicleの参照です。

public class Test { 
    public static void main(String[] args) { 
     Vehicle v = new Car(); 
     Bike b = (Bike) v; 
     // some stuff 
    } 
} 
+1

JVMは、例外をスローしているときにJVMがカーであることを認識しているためです。 –

+0

コンパイラは例外を分割しません。コードは**ランタイム** ClassCastExceptionをスローします。 –

+0

@Pregnantママ、もしあなたがそれらのどれかに満足すれば答えを受け入れてください。 – Reddy

答えて

3

これは実行時例外であるため、エラーメッセージにはCarと表示されます。この時点では、Vehicle参照が指す実際のインスタンス(Car、Bike、またはVehicle)を知っているので、より具体的なエラーメッセージが表示されます。

コンパイル時に例外がある場合、コンパイラはVehicle参照が指している実際のインスタンスを認識できないため、Vehicleを記述していました。

+0

意味があります!ありがとう。 – m0therway

1

実際にはキャストされているのはCarです。 vVehicleであり、CarVehicleであるため、Vehicle v = new Car();の割り当てが機能します。

オブジェクトvは、そのIDを保持します。それはCarです。したがって、違法キャストはCarからBikeになります。 vが渡された、と言う、場合Vehicle

0

ライン

Bike b = (Bike) v; 

は法的になります。だから私はこの検証が最適化の過程で起こっていると思います。コンパイラはキャスト時の通常の作業を最適化したい場合があります。bを完全になくして最適化したい場合もあります。vBikeとして作成した場合は、Carではなくとなります。

+0

vオブジェクトがどこから来るかにかかわらず、vがBikeオブジェクト(またはサブクラスのインスタンス)である場合にのみ、その行は有効です。 –

0

A(半)プレーン英語応答:バイクは異なる特性(変数)を有することになるので

A車が突然、「なる」自転車やバイクのように治療することができないがそれをを記述し、異なりますへの道はそれ(方法)とと対話する。

しかし、それらは両方の車両であるため、おそらく、操舵する能力、左または右に回転する能力、歯車を変更する能力など、共通のものがあります。

あなたはこのようにロジックを持っているとき、これは、それが簡単になります:

ArrayList<Vehicle> vehicles = new ArrayList<Vehicle>(); 
vehicles.add(new Bike()); 
vehicles.add(new Car()); 
vehicles.add(new Bike()); 

//Some other crazy code 

for(Vehicle v : vehicles) { 
    v.applyBrakes(); 
    v.changeDownGear(); 
    v.turnRight(); 
} 

車両(自転車、車、セグウェイなど)の各サブクラスは、これらのメソッドの独自の実装を持っているし、適切

0

を自分自身を扱うでしょうソースコードがなければ、正当なものとそうでないものを明確に言うことは不可能です。しかし、それはこれらのクラスの継承ツリーが

Vehicle 
     | 
    __________ 
    |   | 
Car  Bike 

CarBikeVehicleCarBikeを一般化したものであることを意味Vehicleのサブクラスであることをこのようなようなものになりますと仮定しても安全です。 Javaでは、サブクラスのインスタンスをその基底クラスにキャストできます。この場合、Carを車両にキャストし、実際にVehicleオブジェクトのインスタンスがあるように扱うことができます。同じことがBikeの場合も同様です。ただし、CarBikeのサブクラスではないため、一方から他方にキャストすることはできません。すべてCarsVehiclesですが、すべてではありませんVehiclesCarsです。それらはまたBikesではありません。 Carは決してBikeであり、その逆もありません。

これを実行すると、より拡張性のあるコードを作成できます。たとえば、将来書き込まれるコードとのやり取りを理解するコードを書くことができます。これの例としては、他の開発者が後でカスタム実装を提供できるような共通インターフェイス(drive()など)があります。しかし、新しいサブクラスをあたかもそれらが基本クラスのインスタンスであるかのように扱うことができるので、あなたのコードは手で書くことができます。

関連する問題