1

同じ抽象オブジェクトから拡張されたさまざまなオブジェクトを単一のコンテナーに格納し、それらのオブジェクトのすべてのカスタム フィールドにアクセスできるようにすることは可能ですか? 例を挙げましょう。フォードとホンダの 2 台の車があるとします。すべての車には重量と色があるため、次の抽象クラスを作成できます。

public abstract class Car{

  private double weight; 
  private String color;

  public Car(){
    this.weight=0;
    this.color="";
  }
  ...getters and 
  ...setters
}

ここで、Ford クラスに追加フィールド ' radio ' があり、次のようになっているとします。

public Ford extends Car(){
private String radio;

public Ford(){
super();
this.radio = "generic";
}
}

同様に、Honda クラスにはカスタム フィールド ' camera 'があります。

public Honda extends Car(){
  private String camera;

  public Honda(){
    super();
    this.camera= "analog";
  }
}

以下のように、これらのクラスのインスタンスを単一のコンテナーに保持することは可能ですか。以下のコードは機能しますが、これは私が望むものではないことに注意してください。以下のコメントを参照してください。

Ford ford = new Ford();
Honda honda = new Honda();
ArrayList<Car> myCars = new ArrayList<Car>();
myCars.add(ford);
myCars.add(honda);

ここに私の問題があります:myCars.get(0)がクラスのオブジェクトを取得するCarと(明らかに)、カスタムフィールドradioを取得できません。もちろん、私は次のようなことを行うことができ、無線((Ford) myCars.get(0))フィールドを見ることができますが、ダウンキャストなどを行わずにすべてのフィールドを明らかにするより良いコンテナを作成することは可能ですか: - Fordクラスを返し、私はweight、color、radioへのアクセス - Hondaクラスが返され、 weight、color、およびcameraにアクセスできるようになります。 myContainer.get(0) myContainer.get(1)

私の勘では、解決策は近いし、それも可能ですが、私の Java の専門知識はまだそこまで達していません。たぶん、ある種のジェネリックまたはハッシュマップに関係しているでしょうか??

君たちありがとう!!

4

3 に答える 3

2

いくつかの選択肢がありますが、あなたの理想を完全に満たすものはありません。

  • クラス内の特定のプロパティのすべてのゲッターを追加し、適用できない場合に例外をCar返すかスローすることができます。Null
  • Visitor パターンを適用できます。
  • CarContainerリストをラップし、特定のタイプのすべての要素を返すメソッドを持つクラスを作成できますList<Ford> getAllTheFords()。このようにして、コンテナ クラスの醜いキャストを隠すことができます。

個人的な好みに応じて代替案をリストしました:-)

于 2012-08-08T15:54:56.747 に答える
2

あなたができることは、ジェネリックを使用することです。

リポジトリは次のメソッドを実装できます。

public static <T extends Car> T getFromRepository(Class<T> type, Object key) 
public static <T extends Car> boolean addToRepository(Class<T> type, Object key, T value)

次に、これを次のように呼び出すことができます (フォードのキーを既に持っていると仮定します):

Ford ford = Repository.getFromRepository(Ford.class, fordKey)

もちろん、特定のタイプのすべてのオブジェクトを取得するメソッドを実装できます...

PS: サブクラスで同じメソッドを使用できる場合の簡単な代替方法は、テンプレート メソッド パターンです: http://en.wikipedia.org/wiki/Template_method_pattern

于 2012-08-08T15:55:17.677 に答える
1

myCars.get(0)Ford オブジェクトを返します。ただし、これは実行時にのみ認識されます。問題は、 を呼び出すcar.radioには、それが Ford であることを知る必要があり、そうでない場合はそのメソッドを呼び出すことができないことです。したがって、いずれにしても、タイプとキャストを確認する必要があります。

List<Accessory>1 つの解決策は、抽象クラスにフィールドを追加することです。

次のようなものを書くことができます:

Car car = cars.get(0);
if (car.hasAccessories()) {
    car.getAccessory(0).operate();
}

それがユースケースに必要かどうかはわかりません。

于 2012-08-08T15:55:15.837 に答える