2016-04-12 3 views
0

私がやりたい何鋳造オブジェクトは

public enum MyEnum { 
     member1(MyClass1.class){ 
      @Override 
      public void doStuff(Object obj) { 
       ... 
      } 
     }, 
     member2(MyClass2.class){ 
      @Override 
      public void doStuff(Object obj) { 
       ... 
      } 
     }; 
     ... 
     public abstract void doStuff(Object obj); 
    } 

は、このような列挙型でメソッドを呼び出すことである列挙型のこの種を持っていますどのオブジェクトにキャストしなければならないか列挙する私が渡すmyObjectはMyClass1です。 member1は、enumメンバー記述でも定義されているMyClass1だけを期待していることを自動的に認識する必要があります。

このようなことも可能ですか、まったく間違った経路を歩いていますか?

+3

完全に間違ったパスです。ごめんなさい。最初から始めて、それをしようとしているのではなく、何をしようとしているのかを説明してください... –

答えて

3
public enum MyEnum { 
    member1(String.class){ 
     @Override 
     public void doStuff(Object obj) { 
     this.checkArgumentType(obj); 
     String stringObj = (String) obj; 
     //... 
     } 
    }, 
    member2(Integer.class){ 
     @Override 
     public void doStuff(Object obj) { 
     this.checkArgumentType(obj); 
     Integer stringObj = (Integer) obj; 
     //... 
     } 

    }; 

    private final Class<?> clazz; 

    MyEnum(Class<?> clazz) { 
     this.clazz = clazz; 
    } 

    void checkArgumentType(Object obj) { 
     if (!clazz.isAssignableFrom(obj.getClass())) { 
     throw new IllegalArgumentException("Wrong class"); 
     } 
    } 

    //... 
    public abstract void doStuff(Object obj); 
} 
+0

私はこれが好きです。ありがとうございました!秒の答えも面白かったですが、実際にはとても狂っていました。 – Kaspar

+1

これは型セーフではないことに注意してください。間違ったタイプのオブジェクトを渡すと、コンパイル時にエラーが発生することはありません。代わりに実行時に例外が発生します。一般に、実行時ではなくコンパイル時にエラーをキャッチするほうがよいです。 – Jesper

+0

さて、** **タイプセーフです。コンパイル時の型セーフではありません。 – Vampire

2

何か同様のことが可能ですが、別のクラスを作成することについて考えなければならないほど、面倒で複雑なものになります。しかし、あなたは何ができるか、例として:

public enum Foo { 

    member1(new Bar<String, Long>(Long.class){ 

     @Override 
     void doStuff(String aString) { 

     } 

    }); 

    private final Bar<?,?> bar; 

    private Foo(Bar<?,?> bar) { 
     this.bar = bar; 
    } 

    private static abstract class Bar<A,B> { 

     private final Class<B> type; 

     Bar(Class<B> type) { 
      this.type = type; 
     } 

     abstract void doStuff(A a); 
    } 
} 
+0

目の胸を通って、確かにちょっと後ろから、素晴らしい解決策です。 :-D – Vampire

0

これは、あなたが心の中でそれを持っている方法で、enumでは不可能です。

理想的には、コンパイル時の安全性が必要です。 Objectを渡してから、型キャストはできません。何も間違った種類のオブジェクトを渡すことを妨げるものはなく、オブジェクトを実行しないときにオブジェクトをキャストしようとすると、ClassCastExceptionが実行時に実行されるまでそのことを知ることはできません。

列挙型は、型パラメータを持つことができませんので、あなたはこのように、型パラメータで何もできない。

:あなたは型の安全性が必要な場合

// This is not valid Java! 
public enum MyEnum<T> { 
    member1<MyClass> { 
     @Override 
     public void doStuff(MyClass obj) { ... } 
    } 

    // ... 
    public abstract void doStuff(T obj); 
} 

、だけではなく、enumの定数の束を使用します

interface MyConstant<T> { 
    void doStuff(T obj); 
} 

public final class MyConstants { 

    public static final MyConstant<MyClass1> MEMBER_1 = new MyConstant<MyClass1>() { 
     @Override 
     public void doStuff(MyClass1 obj) { 
      // ... 
     } 
    }; 

    // etc. 

    private MyConstants() { 
    } 
}