3

ジェネリック クラスで動作する必要があるが、列挙型で特定のインターフェイスを実装するものに制限する必要があるユーティリティ クラスがあります。

// These two work
Class<? extends Enum<?>> enumClass;
Class<? extends MyInterface> interfaceClass;

// This is what I want but does not work
Class<? extends MyInterface & Enum<?>> enumAndInterfaceClass;

ジェネリックの場合、これを正常に使用できます

public class MyClass<T extends Enum<T> & MyInterface> {
    public MyClass(Class<T> theClass) {
        ...
    }
}

ただし、どこでもジェネリックを使用することはできず、個別に宣言する必要があります。これが可能かどうかはわかりません。
私の質問は、これらの制約を使用してメンバー変数を宣言するにはどうすればよいですか?

したがって、現在 MyClass はシングルトンであり、必要に応じて列挙型/インターフェイスを更新できます。その操作の戻り値は、与えられた列挙型によって異なります。列挙型を変更するたびに新しいインスタンスを作成する必要があるため、ジェネリックを使用したくありません。すでに多くのコードが使用されているため、シングルトンから逸脱することは承認されません。したがって、参照を保持する必要があります。インターフェイス要件を強制することしかできなかったと思います。それ以外の場合は例外をスローする列挙型であることをセッターメソッドでチェックインしますが、それは理想的ではありません。

編集(質問を更新し、詳細を追加)

4

2 に答える 2

2

私が覚えている限りでは、クラスとメソッドの型パラメーターに対してのみ交差型(これが作成するもの) を宣言できます。&交差型を持つローカル変数を直接宣言することはできません。milkplusvellocet の回答に見られるように、クラスまたはメソッド型パラメーターを使用してそのような変数を作成できます。

同様の質問に対するこの回答の JLS リファレンスを参照してください: https://stackoverflow.com/a/6643378/282229

于 2012-04-05T22:53:22.787 に答える
2

これはうまくいくはずです:

public interface MyInterface {

    void foo();
}

public final class Utils {

    public static <E extends Enum<E> & MyInterface> void doWork(Class<E> clazz) {
        for(E enumConstant : clazz.getEnumConstants) {
            enumConstant.foo();
        }
    }
}

編集キャプチャされた型をローカル変数として使用することについてのあなたの行に気づきませんでした。もちろん、これはパラメーター化されたメソッドの本体全体で使用できます。上記の改訂されたスニペットを参照してください。

于 2012-04-05T22:51:15.310 に答える