C 中,資料處理層之資料庫基類

2022-02-22 03:08:08 字數 4384 閱讀 9464

做開發也有將近2年的時間了,但是經驗其實也不多。經歷過幾個小公司,資料處理層使用過基本的sql,也有nhibernate框架。框架確實好用,省去了不少**量,但是業務複雜的情況下,也就難以依託了,仍然需要自己手動書寫sql。業餘開發專案的時候資料層使用了框架,後來改回了基礎的sql底層,原因嘛,也想說自己在重複造輪子的情況下,能有其他的收穫。

原本使用泛型版本的底層基類,無法使用多型,因此也就無法使用工廠模式建立對應的sql介面了。

原資料庫基類:

1

///2

///資料庫連線基類

3///

4///

資料庫連線池

5///

資料庫command

6///

資料引數

7///

資料庫讀取流

8///

資料庫adapter

9///

事務10

public

class basedb

11where dbconn : dbconnection, new()

12where dbcmd : dbcommand, new()

13where dbparam : dbparameter, new()

14where dbreader : dbdatareader

15where dbadapter : dbdataadapter, new()

16where dbtrans : dbtransaction

17

資料庫派生類:

1

///2

///ms-sql資料庫連線

3///

4public

class mssqldb : basedb5 8

9///

10///

access資料庫

11///

12public

class oledb : basedb

13

這種情況下,除非使用4.0的新特性「協變」,否則無法通過基類來接收對應的派生類了。

其實資料層的基類無非就是dbconnection、dbcommand、dbparameter等,差異的地方無非就是在例項化dbconnection、dbcommand、dbdataadapter這些,因此我們只要讓派生類去重寫返回dbconnection、dbcommand、dbdataadapter對應的派生類就可以了。

抽象方法如下:

1

///2

///新資料庫連線池

3///

4///

資料庫連線字串

5///

6protected

abstract dbconnection newconn(string connectionstr);78

///9

///新sql解析方式

10///

11///

12protected

abstract dbcommand newcommand();

1314

///15

///新dataadapter

16///

17///

18protected

abstract dbdataadapter newadapter();

資料庫基類就做好了,這時候我們使用了幾次之後,就會發現在獲取dbdatareader的時候,要自己重複的寫如下**:

1 abstractbasedb db = //

相應的派生類;

2using(dbdatareader reader = db.executereader(引數))

6 }

於是乎,就有了想把dbdatareader直接轉換成對應實體類的想法,既然有了想法我們就動手開始寫吧。

要將dbdatareader內的資料庫輸出流轉化為對應的實體類泛型,其實就是將每一行值進行轉換而已,這時候我們可以用泛型去定義,因為實體類需要例項化,因此我們需要這個t必須是可以例項化的。

**如下:

1 ilistclasslist = new list();

2 propertyinfo properties = typeof(t).getproperties();

3 predicatematch;

4while (this.datareader.read())

5 16 }

17 classlist.add(tobj);

18 }

做到這裡的時候,可能有些人已經想到了乙個問題,那就是如果實體類屬性名跟資料庫的列名不相同(**生成的時候對資料庫列名進行了處理)怎麼辦呢,那這個時候,我們就需要提供乙個可以將資料庫列名進行轉化的方法,該委託出場了。

修改後**如下:

1

///2

///轉化為類泛型

3///

4///

引用型別

5///

格式化列名

6///

7ilisttolist(func format) where t : new()

8 22 match = p => p.name == filedname;

23if (!this.datareader.isdbnull(i) && array.exists(properties, match))

24

28 }

29 classlist.add(tobj);

30 }

31return classlist;

32 }

以上加入了引數func,並且在獲取列名的時候,判斷如果格式化方法存在,則對列名進行處理,到這裡將dbdatareader轉化為實體類泛型就完成了,然而完成到這裡我們就會有了新的想法了,既然實體類已經實現了,那麼如果t是基礎型別怎麼辦呢,於是乎我們要過載這個方法,讓他也可以適用於基礎型別泛型。

進一步改進以後,**如下:

1

///2

///將datareader轉化為泛型

3///

4///

需要轉化的實體類型別

5///

格式化列名

6///

7public ilisttolist(func format) where t : new()

8 15

else

16

19return list;

20 }

2122

///23

///轉化為值型別泛型

24///

25///

值型別型別

26///

27ilisttovaluelist()

28 35

return valuelist;

36 }

3738

///39

///轉化為類泛型

40///

41///

引用型別

42///

格式化列名

43///

44ilisttoclasslist(func format) where t : new()

45 59 match = p => p.name == filedname;

60if (!this.datareader.isdbnull(i) && array.exists(properties, match))

61

65 }

66 classlist.add(tobj);

67 }

68return classlist;

69 }

這樣轉化為泛型的方法就比較ok了。於是又使用了一段時間,發覺業務邏輯複雜的時候,返回的資料可不止一張表,也可能是多張表的資料一起返回的,這個時候除了可以使用datatable以外,沒有其他的方法可以用了。想到了在nhibernate獲取資料的時候,可以返回ilist型別,接下來我們也可依葫蘆畫瓢也做乙個這樣的轉換。

轉換的方式其實跟轉換為類泛型是差不多的,在迴圈dbdatareader.fieldcount的時候,我們只要將迴圈的資料放入arraylist內就可以了。

具體**如下:

1 ilist sublist = new arraylist();

2while (this.datareader.read())

3 10 sublist.add(list);

11 }

12return sublist;

海量資料處理之資料庫索引

一,什麼是索引 資料庫索引好比是一本書前面的目錄,能加快資料庫的查詢速度。例如這樣乙個查詢 select from table1 where id 44。如果沒有索引,必須遍歷整個表,直到id等於44的這一行被找到為止 有了索引之後 必須是在id這一列上建立的索引 直接在索引裡面找44 也就是在id...

資料庫資料處理故事多

每年評教都會遇到資料匯入的一系列問題。從中收穫頗豐。這兩天別人總在問我,你們基礎出了什麼問題,為什麼總在導資料。資料沒問題,為了做足準備,我們需要將8期版的最全的資料整理到10期資料庫中。背景介紹 問題在於從8期版基礎系統到10期版基礎系統在資料庫設計方面有了很大的變化,例如10期學生表中存放著班級...

ORACEL資料庫資料處理 增

給大家介紹乙個簡單oracel資料庫資料處理 增 資料操縱語言 dml data manipulation language 資料操縱語言 可以在下列條件下執行 向表中插入資料 修改現存資料 刪除現存資料 事務是由完成若干項工作的dml語句組成的 insert into插入資料 為每一列新增乙個新值...