2017-03-04 111 views
0

我下載了一個項目以學習Java,並且我找到了修改一些大塊代碼的有趣方法。
我還是Java的新手,我不知道我做了什麼更有效或危險......
語法1是before,而語法2是我的方法。使用枚舉和反射在類列表上調用方法

語法1:

class Person{ 

    TestClass testClass; 
    TestClass2 testClass2; 
    //etc... 

    public Person(){ 
     testClass = new TestClass(); 
     testClass2 = new TestClass2(); 
     //etc... 
    } 

    void init(){ 
     testClass.init(); 
     testClass2.init(); 
     //etc... 
    } 



} 

語法2:

而不是做:

person.testclass.doThing(); 

該方法使用一個散列映射並存儲類爲對象和用途一個枚舉作爲關鍵。

TestClass tc = (TestClass) person.attribute.get(EnumKey.TEST_CLASS); 
tc.doThing(); 

class Person{ 

    public HashMap<EnumKey, Object> attribute; 

    public Person(){ 
     Class2.sendTasks(this); //sends all classes 
    } 

    void init(){ 
     class2.initTasks(this); //inits all 
    } 



} 

class Class2{ 

    void sendTasks(Person p) 
     for (EnumKey ek : EnumKey.values(){ 
      try { 
       p.attribute.put(ek, ek.handshakeClass.newInstance(); 
      } catch (Exception e) { 
       e.printStackTrace(); 
      } 
     } 
    } 

    void initTasks(Person p){ 
     for (EnumKey ek : EnumKey.values(){ 
      (TaskClass) tc = p.attribute.get(ek); //NOTE: all stored values (testclass1,2,3,etc) implement the interface TaskClass... 
      tc.init(); 
     } 
    } 

} 

enum EnumKey{ 

    TEST_CLASS(TestClass.class), 

    TEST_CLASS2(TestClass2.class); 


    Class<?> handshakeClass; 
    EnumKey(Class<?> handshakeClass){ 
     this.handshakeClass = handshakeClass; 

    } 
} 

語法2非常容易,因爲每次創建新類時都不必輸入TaskClass的所有抽象方法。
我可以創建一個新的枚舉字段,剩下的就完成了。

但是這種方法好嗎?它有效嗎?它慢嗎?還是有風險?

回答

1

效率高嗎?它慢嗎?

你正在使用「反射」,所以,是的,那裏有一些開銷。

另一種可能性是建立HashMap中立即

HashMap<Integer, Object> attribute = new HashMap<>() {{ 
    put(0, new TestClass()); 
    put(1, new TestClass1()) ; 
}}; 

這是一個好的方法?

這確實取決於你需要做什麼,但它是迭代類似類的列表並動態更新其他對象的最簡單方法,是的。

您可以使用接口和抽象類進一步擴展。

有風險?

不是我所知道的。

還有其他的方法可以做到,你有什麼不一樣遍歷所有文件在類路徑枚舉,但我要說枚舉更安全

+0

有沒有什麼辦法讓周圍的反射?我試圖做到這一點,所以枚舉字段的領域(對於缺乏術語)是新的TestClass(),而不是TestClass.class,然後是newInstance,但這樣每個人的TestClass是相同的...而不是實例.. – user7148508

+0

如果您需要多個實例,則必須多次調用'new'。您可以直接構建'attribute'哈希映射,就像您擁有枚舉一樣。 –

+0

是否有默認的java方法來執行:new TestClass()。newInstance();而不是使用TestClass.class.newInstance();因此不需要反射 – user7148508