簡體   English   中英

標准化java構造函數以供反射使用

[英]Standardising a java constructor for use by reflection

我有一個PropertyBag類,它模擬一組可被對象消耗的屬性。

我還有幾個類A1, A2, ..., AN ,它們具有表單的構造函數

public A...(PropertyBag);

所有這些類都實現了接口 iA

我使用反射來創建相關的A...傳遞PropertyBag 我從PropertyBag對象中提取數據以生成該類的候選成員數據。

我希望能夠做的是在編譯時強制A...類的實現者來實現上述形式的構造函數。 我知道我的要求很奇怪:你為什么要標准化施工參數? 但我在這里有一個案例。

當然,我可以做的是有一個單獨的構造和初始化步驟,因為我可以將初始化函數標記為抽象,甚至可能將iA更改為包含該抽象初始化函數定義的抽象類。 我會用反射來調用初始化。 如果任何A...缺少初始化函數,這將給我編譯時失敗。 但我不喜歡將構造和初始化分離為構造但未初始化的對象沒有意義的想法。

我在這里錯過了一招嗎? (在C ++中,我可以在編譯時使用模板強制執行,但在Java中看不到某種方式)。

我希望能夠做的是在編譯時強制A類的實現者來實現上述形式的構造函數。

你不能,我害怕。 Java中沒有任何內容可以強制執行。

可以做的是編寫一個單元測試,找到實現接口的所有類(例如,通過查找jar文件中的所有類),然后檢查它們是否具有這樣的構造函數。 它不如編譯時安全,但它總比沒有好。

盡管什么喬恩說,還有一個辦法,迫使一個構造函數。

從界面iA創建一個抽象類。 在這個抽象實現中,您可以定義所需的構造函數,並確保沒有默認構造函數。

讓所有類擴展抽象實現。 他們將不得不實現一個構造函數並調用超級構造函數(這是你將初始化代碼放在哪里)。

雖然有一個問題。 實現的構造函數可以具有任何簽名(默認簽名除外)。

也許這個技巧可以幫助你。

您可以通過為構造函數創建抽象來間接實現此目的:

public class ConstructionTest {

    private interface Constructed { // iA in the question
        // some methods
    }

    private static class PropertyBag {

    }


    private interface Constructor {
        public Constructed construct(PropertyBag bag);
    }

    public class TestConstructor implements Constructor {

        public Constructed construct(PropertyBag bag) {
            return new Constructed() { };
        }

    }

    @Test
    public void testConstruct() {

        Object potentialConstructor = new TestConstructor();
        if (Constructor.class.isAssignableFrom(potentialConstructor.getClass())) {
            Constructor constructor = (Constructor) potentialConstructor;
            Constructed constructed = constructor.construct(new PropertyBag());
            assertNotNull(constructed);
        }
   }
}

這會增加一點點的復雜性,更多的類,更多的接口,並且您可能需要每個iANConstructor實現。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM