2010-10-24 118 views

回答

3

Expandos的兩種常見用途是部分固定模式和deleting舊屬性。

我經常使用Expando,當我有一種跨實體需要稍微不同的屬性時;換句話說,當我需要一個「部分」動態模式時。一個用例是一個應用程序,用於接受某些產品是液體(認爲水),一些是物理單元(認爲DVD),另一些是「其他」(認爲麪粉)的訂單。一些領域,如項目代碼,價格和數量,總是需要的。但是,如果計算數量的細節還需要什麼呢?

通常情況下,固定架構解決方案將爲我們可能使用的所有變量添加屬性:權重,維度,股票權重前後等等。這很糟糕。對於每個實體,其他大部分領域都不需要。

class Order(db.Model): 
    # These fields are always needed. 
    item_code = db.StringProperty() 
    unit_of_measure = db.StringProperty() 
    unit_price = db.FloatProperty() 
    quantity = db.FloatProperty() 

    # These fields are used depending on the unit of measure. 
    weight = db.FloatProperty() 
    volume = db.FloatProperty() 
    stock_start_weight = db.FloatProperty() 
    stock_end_weight = db.FloatProperty() 

With Expando我們可以做得更好。我們可以使用unit_of_measure來告訴我們如何計算數量。計算數量的函數可以設置動態字段,並且讀取該方法信息的函數知道要查找什麼。而且,該實體沒有一堆不需要的屬性。

class Order(db.Expando): 
    # Every instance has these fields. 
    item_code = db.StringProperty() 
    unit_of_measure = db.StringProperty() 
    unit_price = db.FloatProperty() 
    quantity = db.FloatProperty() 


def compute_gallons(entity, kilograms, kg_per_gallon): 
    # Set the fixed fields. 
    entity.unit_of_measure = 'GAL' 
    entity.quantity = kilograms/kg_per_gallon 

    # Set the gallon specific fields: 
    entity.weight = kilograms 
    entity.density = kg_per_gallon 

您可以通過使用text或blob屬性並將「其他」字典序列化爲它來獲得類似的結果。 Expando基本上是爲你自動化的。

+1

您所概述的另一種選擇是使用PolyModel。 – 2010-10-26 11:07:04

+1

你可以;但是您可能會創建並導入大量模型來處理變體(對於此類示例)。我處理液體,並且有很多*(我們的應用程序使用大約12個)方法來計算音量。 – 2010-10-26 15:25:49

+0

Expando模型的最原始的總結之一。謝謝! – Jon 2014-07-11 14:30:55

相關問題