6

ネストされたワイルドカード境界型を持つ境界型パラメーターを持つクラスがあります。クラスでは、バインドされたネストされたパラメーターの型を複数のメソッドで使用する必要があります。複数の場所で簡単に参照できるように、代わりにワイルドカード境界型をジェネリック型パラメーターとして定義するか、ジェネリック変数名に割り当てる方法はありますか?

クラスの実装方法は次のようになります

    class AbstractManager<F extends Filter<? extends Criteria<? extends Type>>>
    {
       protected void setFilter(F filter)
       {
         setCriteria(f.getCriteria());
       }

       protected <T extends Criteria<? extends Type>> void setCriteria(List<T> criteria)
       {   
       }

       protected <T extends Criteria<? extends Type>> void doSomethingWithCriteria(List<T> criteria)
       {
          ...
       }
    }

これは実際にはリストのタイプをフィルターのタイプに制限しませんが、私たちの状況では十分です。理想的には、リストの型は、フィルターの推論された型をメソッドの境界付き型パラメーターのように名前にバインドできる構造体を使用してフィルターの型に制限されますが、代わりにクラス レベルで制限されます。

基本的に私は次のようなことをしたいと思います

    class <G extends Criteria<? extends Type> AbstractManager<F extends Filter<G>>

私が知っていて見つけることができることから、これは不可能ですが、これを可能にするあいまいな機能またはJava 7の新機能がおそらくあることを望んでいました. 次のような2番目の型パラメーターを指定できることは知っています

    class AbstractManager<F extends Filter<G>, G extends Criteria<? extends Type>>

しかし、コンパイラが決定できるときに、子クラスで G を指定する必要はありません。

私が見つけることができた唯一の可能なオプション/解決策は、この質問 の解決策で指定されたファクトリメソッドを持つ浅いサブクラスを持つことですJava および Javaジェネリックのネストされた型パラメーター-同じワイルドカードを複数回使用します

4

1 に答える 1

1

あなたが何をしようとしているのか理解できれば、あなたのクラスのセマンティクスが変わるでしょう。現在のクラスでは、たとえば次のようになります。

class T1 extends Type {}
class T2 extends Type {}
class C1 extends Criteria<T1> {}
class C2 extends Criteria<T2> {}
class C3 extends Criteria<T2> {}
class F1 extends Filter<C1> {}
class Manager extends AbstractManager<F1> {}

そして、Manager は F1 に基づいていますが、一部のユーザー コードは完全に合法です。

Manager m = new Manager();
C2 c2 = new C2();
C3 c3 = new C3();
m.setCriteria(Arrays.asList(new C2[]{c2});
m.doSomethingWithCriteria(Arrays.asList(new C3[]{c3});

それがあなたの意図したものかどうかはわかりませんが、合法です(コンパイラの観点から)。ただし、何らかの方法でそのワイルドカード型に名前を付けることができた場合、メソッドでその名前を使用すると、クラスのユーザーがすべてのメソッドで同じ型を使用するように制限されます。つまり、私の例では、メソッドは のリストで呼び出す必要がありますC1

結論として、例の柔軟性が必要な場合は、ワイルドカードを繰り返す必要があります。ただし、メソッドがマネージャーのフィルターと同じ基準を使用するという制約が必要な場合は、実際にソリューションを提供します。

class AbstractManager<F extends Filter<G>, G extends Criteria<? extends Type>>

(または、あなたが述べたように、繰り返しを避けるために専用のサブタイプを作成します(それで気に入らないことはありますか?))

于 2014-03-28T09:00:24.750 に答える