日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問(wèn) 生活随笔!

生活随笔

當(dāng)前位置: 首頁(yè) > 编程资源 > 编程问答 >内容正文

编程问答

Entity Framework 4 in Action读书笔记——第一章:数据访问重载:Entity Framework(2)...

發(fā)布時(shí)間:2023/12/15 编程问答 28 豆豆
生活随笔 收集整理的這篇文章主要介紹了 Entity Framework 4 in Action读书笔记——第一章:数据访问重载:Entity Framework(2)... 小編覺(jué)得挺不錯(cuò)的,現(xiàn)在分享給大家,幫大家做個(gè)參考.

上一篇講解了通用數(shù)據(jù)容器,這一篇使用類來(lái)組織數(shù)據(jù)。

類是面向?qū)ο缶幊陶Z(yǔ)言的基礎(chǔ)。使用類,你不需要知道具體的存儲(chǔ)機(jī)制,數(shù)據(jù)源可以是數(shù)據(jù)庫(kù),Web服務(wù),XML文件等。類提供了很多優(yōu)勢(shì),尤其是在企業(yè)應(yīng)用中。

1.強(qiáng)類型 2.編譯時(shí)檢查 3.易于開(kāi)發(fā) 4.存儲(chǔ)無(wú)關(guān)

使用類展示數(shù)據(jù)

我們重新從零開(kāi)始。你的客戶想要在表格中展示所有的訂單,第一步就是要新建一個(gè)Order類容納訂單數(shù)據(jù),如下圖所示:

第二步再新建一個(gè)類,這個(gè)類包含一個(gè)從數(shù)據(jù)庫(kù)中讀取數(shù)據(jù)的方法,并將數(shù)據(jù)轉(zhuǎn)換成對(duì)象。這個(gè)容器類通常放在一個(gè)單獨(dú)的程序集里,就是所謂數(shù)據(jù)層。方法代碼如下:

訂單的集合
  • public List<Order> GetOrders()
  • ?{
  • ?????using (SqlConnection conn = new SqlConnection(connString))
  • ?????{
  • ?????????using (SqlCommand comm = new SqlCommand("select * from orders", conn))
  • ?????????{
  • ?????????????conn.Open();
  • ?????????????using (SqlDataReader r = comm.ExecuteReader())
  • ?????????????{
  • ?????????????????List<Order> orders = new List<Order>();
  • ?????????????????while (rd.Read())
  • ?????????????????{
  • ?????????????????????orders.Add(
  • ?????????????????????new Order
  • ?????????????????????{
  • ?????????????????????????CustomerCode = (string)rd["CustomerCode"],
  • ?????????????????????????OrderDate = (DateTime)rd["OrderDate"],
  • ?????????????????????????OrderCode = (string)rd["OrderCode"],
  • ?????????????????????????ShippingAddress = (string)rd["ShippingAddress"],
  • ?????????????????????????ShippingCity = (string)rd["ShippingCity"],
  • ?????????????????????????ShippingZipCode = (string)rd["ShippingZipCode"],
  • ?????????????????????????ShippingCountry = (string)rd["ShippingCountry"]
  • ?????????????????????}
  • ?????????????????????);
  • ?????????????????}
  • ?????????????????return orders;
  • ?????????????}
  • ?????????}
  • ?????}
  • ?}
  • 看到這段代碼,很多人的第一反應(yīng)是,怎么這么多代碼啊?不過(guò)沒(méi)關(guān)系,當(dāng)事情變得復(fù)雜的時(shí)候,類就會(huì)給我們提供更多的幫助了。

    從單個(gè)類到對(duì)象模型

    你已經(jīng)看到怎樣創(chuàng)建一個(gè)單獨(dú)的類以及用數(shù)據(jù)庫(kù)中的數(shù)據(jù)初始化它。但是它真正強(qiáng)大的地方是創(chuàng)建多個(gè)類并將它們彼此聯(lián)系起來(lái)。在數(shù)據(jù)庫(kù)中,Order和OrderDetail之間的關(guān)系被描述為Order表中OrderId列和OrderTable中OrderId列的外鍵約束。從數(shù)據(jù)庫(kù)設(shè)計(jì)的角度,這是正確的方法。但是在面向?qū)ο蟮氖澜缰?#xff0c;這是行不通的。我們創(chuàng)建一個(gè)OrderDetail類并給它一個(gè)OrderId屬性這是沒(méi)有意義的。最好的解決方案就是運(yùn)用類的獨(dú)特性:類的屬性類型可以是用戶自定義的類。也就是說(shuō),在Order類中可以引用OrderDetail對(duì)象的集合,OrderDetail可以引用Order對(duì)象。當(dāng)創(chuàng)建了這些關(guān)系,也就開(kāi)始創(chuàng)建對(duì)象模型了。

    關(guān)系和對(duì)象的不同

    了解面向?qū)ο蠛完P(guān)系的區(qū)別很重要,因?yàn)樗绊懼鴮?duì)象模型或者領(lǐng)域模型和數(shù)據(jù)庫(kù)的設(shè)計(jì)。

    下面就從幾個(gè)方面講述它們的不匹配。

    1、數(shù)據(jù)類型(datatype)

    (1).當(dāng)往數(shù)據(jù)庫(kù)表中添加一列時(shí),必須確定它的類型。現(xiàn)代數(shù)據(jù)庫(kù)支持的類型有char, varchar, int, decimal, date等等。但是涉及到類就同了,數(shù)據(jù)庫(kù)中的int和bigint類型可以跟.NET中的Int32和Int64類型匹配,但是數(shù)據(jù)庫(kù)其他類型就沒(méi)有跟.NET中類型有確切的匹配了。

    (2).在數(shù)據(jù)庫(kù)中可以設(shè)置約束條件,比如說(shuō)給nvarchar類型的數(shù)據(jù)設(shè)置一個(gè)最大長(zhǎng)度。但是在.NET中沒(méi)有nvarchar類型,與此類型相近的就是String類型,如果想設(shè)置最大長(zhǎng)度只能在屬性中或者方法中設(shè)定然后再存儲(chǔ)到數(shù)據(jù)庫(kù)中。

    (3).數(shù)據(jù)庫(kù)可以接受二進(jìn)制數(shù)據(jù),但是二進(jìn)制列不知道這些數(shù)據(jù)代表什么,可能是一個(gè)文本文檔、PDF文件或者圖片。在.NET中可以用Object表示這一列,但是沒(méi)有意義,因?yàn)槟忝鞔_的知道在二進(jìn)制列中存儲(chǔ)的是什么類型的數(shù)據(jù)。如果存儲(chǔ)的是一個(gè)文件,可以用Stream屬性,如果是圖片,那么Images類型是你最佳選擇。

    (4).在SQL Server2005中有DateTime和Small-DateTime,SQL Server2008中新增了Date 和 Time兩個(gè)類型。如你所想,第一個(gè)只存儲(chǔ)日期,第二個(gè)只存儲(chǔ)時(shí)間。在.NET中只有一個(gè)DateTime類來(lái)表示日期和時(shí)間。

    2、關(guān)聯(lián)(association)

    談到關(guān)聯(lián),最大的不匹配就是關(guān)系世界和對(duì)象世界中的關(guān)系是怎樣維持的。

    (1).一對(duì)一關(guān)系

    如果往Order表中加入其他列,這起初看似是一個(gè)小的改動(dòng),不會(huì)有太大危險(xiǎn),但是事實(shí)并非如此,因?yàn)楹芏喑绦蚨家玫竭@個(gè)表。替代方法是新建一個(gè)表,用OrderId作為主鍵,在這個(gè)表中加入新增的列。數(shù)據(jù)庫(kù)中這是一個(gè)合理的權(quán)衡辦法,如果在對(duì)象模型中也這么做,那就沒(méi)有意義了。最好的方法就是在Order類中添加一個(gè)屬性。如下圖所示:

    (2).一對(duì)多關(guān)系

    在數(shù)據(jù)庫(kù)中表示“多”一方的表包含父表中的主鍵。例如,在OrderDetail表中包含一個(gè)連接到Order的OrderId列,數(shù)據(jù)庫(kù)術(shù)語(yǔ)稱為外鍵。從本質(zhì)上講,數(shù)據(jù)庫(kù)表的關(guān)聯(lián)既是單一的又是雙向的。單一的是指只需在OrderDetail一方定義關(guān)系,在Order表上不需定義任何東西。雙向是指即使你只修改一方,也會(huì)影響到另一方。這是可能的,因?yàn)镾QL允許你在數(shù)據(jù)表間執(zhí)行聯(lián)合查詢。

    在面向?qū)ο笫澜缰?#xff0c;不存在這種機(jī)制,因?yàn)槊繕訓(xùn)|西都是明確聲明的。OrderDetail類通過(guò)Order屬性到Order的引用,這一點(diǎn)有點(diǎn)像數(shù)據(jù)庫(kù)。實(shí)際的不同你也必須修改Order類,添加一個(gè)包含OrderDetail對(duì)象集合的OrderDetails屬性。這種關(guān)系如下圖所示:

    (3).多對(duì)多關(guān)系

    多對(duì)多關(guān)系中,表與表之間的關(guān)系沒(méi)有主次之分。例如你有Product和Supplier表,你不能簡(jiǎn)單的在一個(gè)表上創(chuàng)建外鍵表示它們的關(guān)系。Product和Supplier表只包含它們自己的數(shù)據(jù),這樣一來(lái),兩個(gè)表不能直接相連,需要依靠第三個(gè)表。

    在對(duì)象模型中的做法是創(chuàng)建Product和Supplier兩個(gè)類。在Product類中添加一個(gè)包含Supplier對(duì)象集合的Suppliers屬性,同樣,在Supplier類中添加一個(gè)包含Product對(duì)象集合的Products屬性。如圖所示:

    3、顆粒度(granularity)

    granularity在這里不知道怎么翻譯比較合適,暫且翻譯成顆粒度吧。顆粒度問(wèn)題指的是類的個(gè)數(shù)和數(shù)據(jù)庫(kù)中表的個(gè)數(shù)不一致。一對(duì)一關(guān)系中,有兩個(gè)表Order和Order2,但是只有一個(gè)Order類。還是讓我們看例子吧。

    在Order表中有一個(gè)送貨地址,被分成了4列:address,city,zip code和country。如果你還要處理其他地址,比如賬單地址,你還要在Order表中添加4列。如圖所示:

    在Order類中已經(jīng)送貨地址的四個(gè)屬性,所以再添加四個(gè)也不會(huì)有問(wèn)題,盡管它工作的很順利,這些屬性會(huì)使類變得越來(lái)越大,越來(lái)越難懂。更重要的是,customers和suppliers表中有地址,或者其他還有地址。類可以重用,創(chuàng)建一個(gè)AddressInfo類,然后重用它不是更好嗎?下面是重構(gòu)完的代碼:

    AddressInfo類和Order類
  • public class AddressInfo
  • {
  • ????public string Address { get; set; }
  • ????public string City { get; set; }
  • ????public string ZipCode { get; set; }
  • ????public string Country { get; set; }
  • }
  • public class Order
  • {
  • ????public Address ShippingAddress { get; set; }
  • ????public Address BillingAddress { get; set; }
  • }
  • 4、繼承(inheritance)

    繼承不匹配指的是在數(shù)據(jù)庫(kù)中實(shí)現(xiàn)繼承是不可能的。我們添加一個(gè)Customer類來(lái)完善對(duì)象模型,然后讓Customer和Supplier類都繼承自Company。在關(guān)系型數(shù)據(jù)庫(kù)中你不能簡(jiǎn)單的聲明Customer表繼承自另一個(gè)表。你可以創(chuàng)建一個(gè)包含Customer和Supplier數(shù)據(jù)的表或者是單獨(dú)創(chuàng)建。不管選擇哪種方式,在數(shù)據(jù)庫(kù)和對(duì)象模型都存在不匹配的問(wèn)題。

    在對(duì)象模型中,有一個(gè)Product類。一個(gè)商店各種各樣的產(chǎn)品,如鞋子,襯衫,高爾夫設(shè)備,有用設(shè)備等等。這些東西都有一些共有的屬性,如價(jià)格和顏色等。即使在這樣一個(gè)例子中,繼承也會(huì)對(duì)你有所幫助。現(xiàn)在創(chuàng)建一個(gè)Product類,然后為每一個(gè)具體的產(chǎn)品創(chuàng)建類。但是當(dāng)你設(shè)計(jì)OrderDetail類的時(shí)候問(wèn)題出現(xiàn)了,在OrderDetail類中,需要一個(gè)屬性指定是哪個(gè)產(chǎn)品的訂單詳細(xì)信息。即使在運(yùn)行時(shí),這個(gè)屬性的類型都是Product,具體對(duì)象的實(shí)例可能是鞋子,襯衫或者任何繼承自Product類型的產(chǎn)品。如圖所示:

    這種類型的結(jié)構(gòu)稱為多態(tài),在數(shù)據(jù)庫(kù)中是不可能表示的。

    5、標(biāo)識(shí)(identity)

    數(shù)據(jù)庫(kù)表中標(biāo)識(shí)一行的是主鍵,因此你為一個(gè)表選擇主鍵時(shí)一定要注意。有時(shí)候你可能想使用自然鍵(natural key),比如產(chǎn)品的代碼,但是這種選擇有可能帶來(lái)麻煩。假如你要修改產(chǎn)品的代碼,因?yàn)槟爿斿e(cuò)了。但是產(chǎn)品代碼在OrderDetail表中是外鍵,所以你必須更新OrderDetail表中的產(chǎn)品代碼。問(wèn)題是你不能更新OrderDetail表中的產(chǎn)品代碼,因?yàn)槿绻阈薷牡闹翟赑roduct表中不存在就會(huì)出現(xiàn)錯(cuò)誤。另一方面,你不能修改Product表中的值,因?yàn)檫`反了外鍵約束。

    這看起來(lái)是最惱人的問(wèn)題了,但是還有一個(gè)原因要避免使用自然鍵。產(chǎn)品代碼可能是比較長(zhǎng)的字符串,但是幾乎所有的數(shù)據(jù)庫(kù)都為存儲(chǔ)和搜索整數(shù)值做了優(yōu)化,所以最有效的主鍵是代理鍵(surrogate key)。代理鍵的使用可以允許你修改其他任何列的值而不用擔(dān)心影響到其他表。

    到目前為止,我們已經(jīng)說(shuō)明了一個(gè)對(duì)象就是表中一行的面向?qū)ο蟊硎?#xff0c;主鍵屬性將對(duì)象和行聯(lián)系起來(lái)。問(wèn)題是,如果比較兩個(gè)相同類型的不同對(duì)象,即時(shí)它們包含了相同的數(shù)據(jù)也證明是不相同的。為什么包含相同數(shù)據(jù)的對(duì)象是不同的呢?因?yàn)槟J(rèn)情況下指向表示數(shù)據(jù)庫(kù)表中同一行數(shù)據(jù)的不同對(duì)象的兩個(gè)變量是不同的。如果兩個(gè)變量指向相同的實(shí)例,那么它們是相等的,這被稱之為“引用相等”。如果有一個(gè)方法可以改變這種默認(rèn)行為,肯定是更可取的。如果兩個(gè)不同的對(duì)象包含相同的數(shù)據(jù),那么它們比較的結(jié)果應(yīng)該返回True。在.NET中,可以重寫Equals和GetHashCode方法到達(dá)同等的效果。

    寫在最后的話

    在前面,我們看到了關(guān)系世界和對(duì)象世界之間存在這么多的不同,下一篇將就這些不同給出解決方案。

    轉(zhuǎn)載于:https://www.cnblogs.com/nianming/archive/2011/08/12/2136508.html

    總結(jié)

    以上是生活随笔為你收集整理的Entity Framework 4 in Action读书笔记——第一章:数据访问重载:Entity Framework(2)...的全部?jī)?nèi)容,希望文章能夠幫你解決所遇到的問(wèn)題。

    如果覺(jué)得生活随笔網(wǎng)站內(nèi)容還不錯(cuò),歡迎將生活随笔推薦給好友。