ADO.NET學習筆記(三)
2024-07-10 13:03:02
供稿:網友
(由于書上的代碼全是用c#寫的,轉換為vb.net實在麻煩,以后就不轉換了,見諒)
五、操縱dataset
在dataset中datarow是其所有數據的基本存放位置,它主要是由一個值數組組成,代表datatable單獨一行。
datarow中主要包括一下幾種信息:1、行中每一列的當前值,2、行中每一列的原始值,3、行狀態,4、父行與子行間的鏈接
初始化一個datarow:
datatable datatable=dataset.tables[0];
datarow newrow=datatable.newrow(); //用datatable生成datarow可以利用datatable里面的模式
datatable.rows.add(newrow);
刪除行:
datatable.rows.remove(行實例);
datatable.rows.removeat(行號);
datarow.delete(); //行自身移除
讀寫datarow的值:
row["列名"],row[列號]均可引用其中的一個屬性
datacolumn a=datatable.columns("列名"); //可以獲得一個列
對行進行批處理更改:
beginedit()開始更改,endedit()結束更改,同時將更改結果寫入dataset,canceledit(),取消更改
例如:
row.beginedit();
對row進行更改
row.endedit();
將數據批量加載到datatable
datatable.beginloaddata();
datatable.loaddatarow(row1,false); //第二個參數為true時,調用datatable.acceptchanges()時接受更改,為false直接添加
……
datatable.endloaddata();
使用這種數據加載方式可以在數據加載期間屏蔽所有的數據約束,索引也不會予以維護,極大的加快了數據加載速度
行的版本:
current:當前值
default:根據操作的不同決定行的default值
original:最后一次調用acceptchanges()之后的值
proposed:調用acceptchanges()之前被更改的值
例如要獲得行的original值:
string oldstring=row("firstname",datarowversion.original);
行的狀態:
row.rowstate獲得行的狀態,例如刪除后變成deleted,數據存儲更新后變為unchanged
六、dataset導航
在ado.net中每個表都保持其相對獨立性,允許在行級上導航不同表之間的相關行(向下導航到子行,向上導航的父行)
如datarow[] invoicerows=custrow.getchildrows("customer_invoice"); //通過關系導航到子行
七、dataview
dataview就時數據視圖,為數據庫結構提供了外模式的實現。
同時dataview也可以為窗體控件和web控件提供數據綁定功能,在每一個datatable中內建了一個dataview為:datatable.defaultview();
創建dataview
dataview sortedview=new dataview(datatable);
對dataview進行排序
datatable.defaultview.sort="lastname";
datatable.defaultview.sort="lastname,firstname desc";
對dataview進行篩選:
1、通過對其中的rowfilter屬性設置可以實現篩選
datatable.defaultview.rowfilter="vendor='rawlings'";
不過篩選表達式只能設置成比較簡單的表達式,功能有限,不過可以滿足基本的要求。
同樣在datatable里面也可以進行簡單的搜索,返回一個datarow數組,例:
datarow[] compoundrows=datatable.select("vendor='wilson' and price>20.00)
2、通過rowstate來篩選
datatable.defaultview.rowstatefilter="dataviewrowstate.originalrows"可以篩選出符合要求狀態的row
對dataview進行搜索:
相對于dataview使用rowfilter進行篩選得到一個矩形數據集,使用find、findrows可以更準確的查找到與特定鍵相匹配的行
搜索的時候必須首先設置dataview的sort屬性:
int found=datatable.defaultview.find("wilson"); //獲得行的位置
datarowview[] rows=datatable.defaultview.findrows("rawlings") //過得一個row數組
八、更新db
在dataset中,每一個datatable對應著一個dataadapter,dataadapter.update()時,datatable自動更新。
更新的時候可以使用commandbuilder自動根據dataset的變化生成更新的sql命令
sqlcommandbuilder bldr=new sqlcommandbuilder(dataadapter);
dataadapter.update(custtable);
不過update接受dataset參數并不更新dataset而是更新dataset中的一個叫"table"的表
使用commandbuilder進行更新的時候要注意一下幾點:
1、selectcommand必須有效
2、必須有主碼
3、若selectcommand填充datatable后架構發生改變,應該在update()之前調用commandbuilder.refreshschema();
4、更新db時不受關系、約束或者dataset中其他表的影響
雖然使用commandbuilder比較方便,不用自己寫更新命令,但自動生成的命令性能不高,這時可以考慮自己編寫存儲過程或直接使用帶參數的sql語句,例如:
string insqry="insert into customer(customerid) values (@customer)";
sqlcommand inscmd=conn.createcommand();
inscmd.commandtext=insqry;
sqlparametercollection insparams=inscmd.parameters;
insparams.add("@customerid",sqldbtype.uniqueidentifier,0,"customerid");
dataadapter.insertcommand=inscmd;
dataadapter.update();
在dataadapter.update()更新時還可以控制更新的范圍:
dataadapter.update(invtable.getchanges(datarowstate.deleted); //只更新被刪除的部分
九、事務
tx=conn.begintransaction(isolationlevel.serializable);
invda.selectcommand.transaction=tx;
事務操作
tx.commit();提交 //tx.rollback();事務回滾
十、數據綁定
簡單版本:(對文本框、標簽等)
{controls}.databindings.add("{property}",{datasource},"{datamember}");
其中property為待綁定的屬性,datasource為dataview或datatable,datamember為datasource其中的某個屬性
復雜版本:(對listbox、combobox等)
要分別設置各個屬性實現綁定:
datasource=支持ilist的一個對象(datatable或dataview)
displaymember:待顯示的datasource中的一個屬性
valuemember:確定在datasource中引用哪一個數據行,即實現與displaymember的名值對應
datagrid綁定:
1、可以設置datasource屬性實現靜態綁定
2、可以使用setdatabinding函數實現動態綁定
同時datagrid支持主控/詳細表顯示
mastergrid.setdatabinding(customertable,"");
detailgrid.setdatabinding(customertable,"customer_invoices") //第二個屬性要設置成關系約束
這樣在主表中選擇一行,在子表中就根據主表行中外碼在子表中找到相應行
綁定之后,綁定項中就有一個currencymanager屬性實現游標功能
bindingcontext[customertable]返回一個currencymanager對象,其中的position屬性可以更改,實現游標的移動。