天天看點

ORM資料層架構的設計熱點:更新指定的列的幾種設計方案ORM架構的定義:對象-關系映射(Object/Relation Mapping,簡稱ORM) 避免思維定式: ORM生成SQL:充血模式的示例:充血模式的兩種更新指定列的設計方案: 貧血模式的示例:貧血模式的兩種更新指定列的設計方案:總結回憶: 

常見的是:資料庫結構=》映射object(實體屬性)=》基于實體類的操作。

還有一種:資料庫結構=》映射object(記憶體表結構)=》基于記憶體表的操作。

當然,如果你有創意,你還能創造出更多的映射載體來實作orm。

由于思維定式,很多開發者,隻有見到基于實體類映射,才會認為是一種orm架構,于是很少人去思考其它映射載體來實作orm。

這個思維定式,和早期在asp.net mvc沒出來之前,把webform架構當成asp.net一樣,于是很少人會去創造另一種開發架構。

不過要避免思維定式,有時候的确不是件容易的事~~~這需要太多知識的沉澱和積累,這個就先不扯了,下面來正題。

一般的資料庫下,都是基于sql語句解析執行的,是以orm最終都避不開生成sql再交還ado.net去執行,進而傳回結果。

由于orm存在映射關系,最簡單的是(字段名稱+資料類型)的實體映射,是以,通常隻要周遊實體的屬性就可以拿到所有字段名稱,進而組合sql去執行了。

而反射的應用,對于實體型映射的orm無疑是佳方案,節省大量代碼;通過反射,在處理時動态獲得指定對象的類型、字段名稱、字段類型、或者特性描述等資訊,進而構造出sql語句。

如果是基于記憶體表(mdatatable)映射的,則無需反射,因為映射的時候,相關結構已提前預約好了,直接周遊擷取即可。

這裡先不說基于記憶體表的映射,說說基于實體映射的設計方案:

ORM資料層架構的設計熱點:更新指定的列的幾種設計方案ORM架構的定義:對象-關系映射(Object/Relation Mapping,簡稱ORM) 避免思維定式: ORM生成SQL:充血模式的示例:充血模式的兩種更新指定列的設計方案: 貧血模式的示例:貧血模式的兩種更新指定列的設計方案:總結回憶: 

    public class users : cyq.data.orm.ormbase

    {

        public users()

        {

            base.setinit(this);

        }

        public int id { get; set; }

        public string username { get; set; }

        public datetime createtime { get; set; }

    }

ORM資料層架構的設計熱點:更新指定的列的幾種設計方案ORM架構的定義:對象-關系映射(Object/Relation Mapping,簡稱ORM) 避免思維定式: ORM生成SQL:充血模式的示例:充血模式的兩種更新指定列的設計方案: 貧血模式的示例:貧血模式的兩種更新指定列的設計方案:總結回憶: 

這種方式,增删改查,都由基類處理了,而基類一般需要三個參數:

1:子類的對象,用于反射類型及屬性的需要。

2:表名(可選,如果不寫,則從反射中拿到類名當表名)

3:資料庫連結(可選,如果不寫,則會預設約定一個配置名稱的資料庫連結)

最終的操作方式類似:

ORM資料層架構的設計熱點:更新指定的列的幾種設計方案ORM架構的定義:對象-關系映射(Object/Relation Mapping,簡稱ORM) 避免思維定式: ORM生成SQL:充血模式的示例:充血模式的兩種更新指定列的設計方案: 貧血模式的示例:貧血模式的兩種更新指定列的設計方案:總結回憶: 

            using (users u = new users())

            {

                u.username = "u1";

                u.update(1);

            }

ORM資料層架構的設計熱點:更新指定的列的幾種設計方案ORM架構的定義:對象-關系映射(Object/Relation Mapping,簡稱ORM) 避免思維定式: ORM生成SQL:充血模式的示例:充血模式的兩種更新指定列的設計方案: 貧血模式的示例:貧血模式的兩種更新指定列的設計方案:總結回憶: 

如果按正常,我們可能會循環所有字段,全部更新;很明顯在這裡我們隻需要更新username。

于是,在設計上,我們需要額外多出一個集合,來存儲字段對應的狀态,這個集合怎麼設計,這個大夥自行發揮了。

這裡的難點,在于,如何設計擷取狀态改變上。

直接切入實體的set屬性,如:

ORM資料層架構的設計熱點:更新指定的列的幾種設計方案ORM架構的定義:對象-關系映射(Object/Relation Mapping,簡稱ORM) 避免思維定式: ORM生成SQL:充血模式的示例:充血模式的兩種更新指定列的設計方案: 貧血模式的示例:貧血模式的兩種更新指定列的設計方案:總結回憶: 

        public string username

            get;

            set

                base.setstate(value);

            }

ORM資料層架構的設計熱點:更新指定的列的幾種設計方案ORM架構的定義:對象-關系映射(Object/Relation Mapping,簡稱ORM) 避免思維定式: ORM生成SQL:充血模式的示例:充血模式的兩種更新指定列的設計方案: 貧血模式的示例:貧血模式的兩種更新指定列的設計方案:總結回憶: 

然後事情就交給基類的setstate方法去修正對應實體的狀态,周遊屬性的時候,再比較狀态,取得隻需要更新的字段去組合即可。

這種方案,優點是:可以保持實體類的相對簡潔,通過在基類利用aop攔截子類的set方法,進而動态的調用setstate方法。

缺點是:實作有點難度,另外是由于aop基類contextboundobject的限制, 内部無法使用泛型。

即你不能實作:select<t>()類似的方法,是以最終的表達式可能需要借第三個類的tolist()方法來傳回,代碼類似:

using(users u = new users())

     list<users> list= u.select().tolist();

具體的方案實作可以見我以前寫的這兩篇文章:

<a href="http://www.cnblogs.com/cyq1162/archive/2012/05/30/2526573.html">c# aop簡單掃盲及orm實體類屬性攔截示例</a>

<a href="http://www.cnblogs.com/cyq1162/archive/2012/08/29/2662492.html">aop realproxy 千年遇bug</a>

ORM資料層架構的設計熱點:更新指定的列的幾種設計方案ORM架構的定義:對象-關系映射(Object/Relation Mapping,簡稱ORM) 避免思維定式: ORM生成SQL:充血模式的示例:充血模式的兩種更新指定列的設計方案: 貧血模式的示例:貧血模式的兩種更新指定列的設計方案:總結回憶: 

    public class users 

    }

ORM資料層架構的設計熱點:更新指定的列的幾種設計方案ORM架構的定義:對象-關系映射(Object/Relation Mapping,簡稱ORM) 避免思維定式: ORM生成SQL:充血模式的示例:充血模式的兩種更新指定列的設計方案: 貧血模式的示例:貧血模式的兩種更新指定列的設計方案:總結回憶: 

這種方式,實體就類似資料載體,本身不具備增删改查功能,類似把基類獨立開來操作。

最終的調用方式可能類似:

ORM資料層架構的設計熱點:更新指定的列的幾種設計方案ORM架構的定義:對象-關系映射(Object/Relation Mapping,簡稱ORM) 避免思維定式: ORM生成SQL:充血模式的示例:充血模式的兩種更新指定列的設計方案: 貧血模式的示例:貧血模式的兩種更新指定列的設計方案:總結回憶: 

users user= dbfast.find&lt;users&gt;(1);//查詢記錄。

users u=new users();

u.username="u1";

dbfast.update&lt;users&gt;(u,1);//更新。 

ORM資料層架構的設計熱點:更新指定的列的幾種設計方案ORM架構的定義:對象-關系映射(Object/Relation Mapping,簡稱ORM) 避免思維定式: ORM生成SQL:充血模式的示例:充血模式的兩種更新指定列的設計方案: 貧血模式的示例:貧血模式的兩種更新指定列的設計方案:總結回憶: 

對于貧血模式,也有兩種對應的設計方案:

ORM資料層架構的設計熱點:更新指定的列的幾種設計方案ORM架構的定義:對象-關系映射(Object/Relation Mapping,簡稱ORM) 避免思維定式: ORM生成SQL:充血模式的示例:充血模式的兩種更新指定列的設計方案: 貧血模式的示例:貧血模式的兩種更新指定列的設計方案:總結回憶: 

    }

ORM資料層架構的設計熱點:更新指定的列的幾種設計方案ORM架構的定義:對象-關系映射(Object/Relation Mapping,簡稱ORM) 避免思維定式: ORM生成SQL:充血模式的示例:充血模式的兩種更新指定列的設計方案: 貧血模式的示例:貧血模式的兩種更新指定列的設計方案:總結回憶: 

由于沒有基類,是以狀态的變化,無法很好的內建的,是以,這種情況的設計,通常需要多一行額外的代碼來傳遞資訊。

例如:

ORM資料層架構的設計熱點:更新指定的列的幾種設計方案ORM架構的定義:對象-關系映射(Object/Relation Mapping,簡稱ORM) 避免思維定式: ORM生成SQL:充血模式的示例:充血模式的兩種更新指定列的設計方案: 貧血模式的示例:貧血模式的兩種更新指定列的設計方案:總結回憶: 

dbfast.setstate&lt;users&gt;("username",state.forupdate);//類似的多了一行來指定需要更新的一個或多個列的狀态。

dbfast.update&lt;users&gt;(u,1);//更新。

ORM資料層架構的設計熱點:更新指定的列的幾種設計方案ORM架構的定義:對象-關系映射(Object/Relation Mapping,簡稱ORM) 避免思維定式: ORM生成SQL:充血模式的示例:充血模式的兩種更新指定列的設計方案: 貧血模式的示例:貧血模式的兩種更新指定列的設計方案:總結回憶: 
ORM資料層架構的設計熱點:更新指定的列的幾種設計方案ORM架構的定義:對象-關系映射(Object/Relation Mapping,簡稱ORM) 避免思維定式: ORM生成SQL:充血模式的示例:充血模式的兩種更新指定列的設計方案: 貧血模式的示例:貧血模式的兩種更新指定列的設計方案:總結回憶: 

        public int? id { get; set; }

        public datetime? createtime { get; set; }

ORM資料層架構的設計熱點:更新指定的列的幾種設計方案ORM架構的定義:對象-關系映射(Object/Relation Mapping,簡稱ORM) 避免思維定式: ORM生成SQL:充血模式的示例:充血模式的兩種更新指定列的設計方案: 貧血模式的示例:貧血模式的兩種更新指定列的設計方案:總結回憶: 

對于這種模式,可以讓值類型的預設值也為null,是以可以通過減免值為null的列,來實作更新值不為null的值。

不過對于這種方式,由于dbnull.value隻能給引用類型指派,是以值類型的字段無法重置為null。

是以,如果要實作對值類型賦null值,可能需要增加一行代碼來對指定的行指定狀态,配合着使用;或者直接操作sql語句。 

記得前些日子和騰訊的架構師面試的時候,好像也交流到了這個指定列的更新的話題上,不過那時候的話題,上升到分布式話題了:

問題:大體是有一份資料載體情況下,使用者更新了某些字段,如何隻更新某些字段的話題:

1:先是說前端的過濾與傳遞隻需要更新的資料(對方:這個先假設沒有做)。

2:服務端可以做緩存,然後比較(對方:假設伺服器有很多,做了負載,如何保證)。

3:全局共享緩存或用分布式緩存(對方:假設沒有分布式緩存,隻有web伺服器緩存,隻有一份副本)

4:通過某種算法,讓使用者的請求的資料對應到相對的副本的伺服器。(對方:算法怎麼實作)

5:。。。此處省略600字了。。。

不知不覺又寫了好幾個小時了,今天就介紹到這裡了~~~謝謝大夥~~~~

最後給貼一下今天各大群熱傳的勵志文:月領1萬2小it職員五年在北京買500萬房子~~

ORM資料層架構的設計熱點:更新指定的列的幾種設計方案ORM架構的定義:對象-關系映射(Object/Relation Mapping,簡稱ORM) 避免思維定式: ORM生成SQL:充血模式的示例:充血模式的兩種更新指定列的設計方案: 貧血模式的示例:貧血模式的兩種更新指定列的設計方案:總結回憶: