1

enum外部システムからを受け取っている状況があり、そのために自分のシステムを返却する必要がありenumます。2つの列挙型には、まったく同じリテラル値が含まれています。

// externalEnum is guaranteed not to be null 
public static MyEnum enumToEnum(final Enum<? extends Enum<?>> externalEnum)
{
    if( externalEnum instanceof MyEnum )
    {
        return (MyEnum)enumType;
    }
    else
    {
        return MyEnum.valueOf(externalEnum.name());
    }
}

ただし、コンパイラは次のように鳴きます。

    [javac]が見つかりました:java.lang.Enum <capture#117 of?java.lang.Enum <?>>を拡張します
    [javac]必須:myEnum
    [javac] if(externalEnum instanceof MyEnum)

単に返すだけで機能するその関数のバージョンを入手しましたMyEnum.valueOf(externalEnum.name())-それは機能し、それが重要です。しかし、私はコンパイラエラーについて困惑しています。

この場合、ジェネリックの具体化プロセスを理解しようとしています。Enum<? extends Enum<?>>またはのインスタンスは(後者が前者のサブタイプ以外のものになることは決してないという条件で)可能性がありますEnum<?>MyEnum

したがって、instanceofテストは機能するはずですEnumが、コンパイラーがその特定のステートメントを吐き出す原因となる何か(およびおそらく列挙型を拡張できないという事実)の一般的な定義に何かがあるようです。

回避策は簡単ですが、問題をよく理解したいので、これに関する洞察をいただければ幸いです。

  • ルイス。
4

4 に答える 4

3

私の(おそらく欠陥のある)問題の分析は、型定義の2つのワイルドカードが互いに分離していることです。

Enum<? extends Enum<?>>

「未知の型を拡張する列挙型を拡張する型の列挙型」を意味します。

あなたが望むものはおそらくもっとこのようなものです:

Enum<T extends Enum<T>>

これは、「それ自体の列挙型を拡張する型の列挙型」を意味します。これは奇妙な再帰的定義です(これはどういうわけかにループバックしますComparable<T>)が、それはsがどのようEnumに定義されるかということです。

もちろん、<T>これを機能させるには、静的メソッドで型パラメーターを使用する必要があります。これを試して:

public static <T extends Enum<T>> MyEnum enumToEnum(final T externalEnum) {
    if (externalEnum instanceof MyEnum) {
        return (MyEnum) externalEnum;
    } else {
        return MyEnum.valueOf(externalEnum.name());
    }
}

編集:間違った識別子によって引き起こされたコンパイラエラーを修正すると、質問のコードがコンパイルされます。だから私の分析は間違いなく欠陥があります;-)

于 2009-11-03T14:38:19.440 に答える
2

両方が同じであるのに、なぜわざわざするのですか?

public static MyEnum enumToEnum(final Enum<? extends Enum<?>> externalEnum)
{
    try
    {
        return MyEnum.valueOf(externalEnum.name());
    }
    catch (Exception ex)
    {
        return MyEnum.UNKNOWN;
    }
}
于 2009-11-03T21:18:28.237 に答える
1

私はあなたがあなたの最初のreturnステートメントでexternalEnumはなく意味していると思います。enumType

これは修正され、Eclipseとantでコンパイルされます。

于 2009-11-03T15:26:19.687 に答える
1

外部システムから列挙型を受け取っている状況があり、そのために自分の列挙型を返す必要があります。

両方のクラスが異なるクラスローダーによってロードされている場合、および/または異なるマイナー/メジャーバージョンを持っている場合、instanceofはfalseを返します。これも考慮に入れてください。

于 2009-11-03T15:29:33.213 に答える