2012-07-15 56 views
2

作爲一個解析器庫的一部分,我的對象層次結構如下:耦合對象層次和操作

 
      ParseEntry 
       | 
       | 
       /\ 
      / \ 
      / \ 
NumericParseEntry StringParseEntry 

等,

這些對象基本保存數據。然後,我有一組操作,比如評估(評估值是否通過解析條目標準),generateSQL(根據解析條目生成SQL條件)。

由於單一職責原則,我不想將這些函數添加到特定的分析條目類,並且想要維護爲分析條目層次結構實現這些功能的單獨層次結構。這允許我爲一個以上的解析條目重用某個實現。

我想知道如何將操作與對象耦合,以便在瀏覽解析表的解析表執行某些操作時,我應該能夠獲得相應的操作對象。

我能想到的一個原始方法是擁有一個工廠類,它在解析條目類型及其相應的評估器/ SQLgenerator之間維護映射。另一種方法是將評估程序/ sql生成器嵌入爲解析條目的數據成員,並將其返回到getter中。

對此即興創作任何幫助將不勝感激。

回答

1

普通數據對象不是非常面向對象的。我認爲操作(evaluate/generateSQL)確實是ParseEntry對象的責任。如果你想重用評估實現,你仍然可以組成一個EvaluatorParseEntry,並委託給它,例如:

public class NumericParseEntry extends ParseEntry { 
    private Evaluator evaluator = ...; 
    private SQLGenerator sqlGenerator = ...; 

    public bool evaluate(Object value) { 
    return evaluator.evaluate(this, value); 
    } 

    public String generateSQL() { 
    return sqlGenerator.generateSQL(this); 
    } 
} 

單一職責原則認爲,應該只有一個原因,一類改變 - 如果您的更改確實與某個具體的ParseEntry有關,那麼更改班級沒有任何問題。


此外,您可以考慮使用繼承和獲得完全擺脫單獨Evaluator/Generator類。例如:

public class NumericParseEntry extends ParseEntry { 
    // put common logic for numeric entries here 
} 

public class IntegerParseEntry extends NumericParseEntry { 
    // put specialized code for handling integers 
} 

public class FloatParseEntry extends NumericParseEntry { 
    // put specialized code for handling floating-point 
} 
+0

感謝您的意見。我同意這樣的觀點:這些操作本質上應該在特定的語法分析類中實現。我喜歡你的想法,將評估代碼移到單獨的層次結構中,並通過合成將它們包含在解析條目中。 – Vikdor 2012-07-16 06:28:34

1

我已經成功地使用這種模式Implementing Complex Case Analysis實施類似的東西,你正在嘗試做的......你就可以創建代碼依賴於類型或無論您選擇的條件以一種很好的方式,不用修改「數據」層次結構。

+0

感謝您的輸入。雖然我個人並不傾向於使用框架來解決我的問題,但這是我通過你瞭解的一個很好的參考資料,可能對未來有所幫助。再次感謝! – Vikdor 2012-07-16 06:29:28

2

對我來說這聽起來像是Visitor Pattern。您將有EvaluatorVisitorSQLGenerationVisitor哪些將有訪問操作ParseEntry s。 ParseEntry元素包含accept(Visitor)操作,其中NumericParseEntryStringParseEntry將延伸。

因爲您使用的是訪客模式,所以單一職責原則是免費的。

+0

感謝您的輸入。我也同意在概念上這些操作可能是訪問者。但是我面臨的問題是在Java中使用Generics在解析條目接口中使用accept方法的簽名來實現它,以便在解析條目的什麼評估者之間具有較強的鍵入。 – Vikdor 2012-07-16 06:26:55