ADO.NET的記憶碎片(六)


校驗DataSet中的數據
數據庫提供了很多的機制使數據是有效的。ADO.NET的DataSet提供了許多可在數據庫系統中使用的相同的數據效驗機制。一般可以將這些效驗的機制分成兩類:列級別的限制和表級別的效限制。列級別的限制:驗證DataColumn的屬性
DataColumn對象提供了許多能用來驗證數據的屬性:
ReadOnly:確保數據是否讓用戶修改
AllowDBNull:一些數據庫的列是否可為Null
MaxLength:最多接受字符串的長度
Unique:是否要求該列是不可重復的
表級別的限制:DataTable類的Constraints集合
ADO.NET對象模型包括兩個類,可以用他們在DataTable中定義約束。這兩個類是UniqueConstraints和ForeignkeyConstraint,他們都是派生於Constraints類的。DataTable公開一個Constraints屬性,使用該屬性可以添加、修改或查看DataTable上的約束。
UniqueConstraints
如果將DataColumn的Unique屬性設置為True,也就在包含該列的DataTable定義了一個唯一的約束。同時還將UniqueConstraints對象加到DataTable對象的Constraints集合中。設置DataColumn的Unique屬性比在DataTable對象的Constraints集合中創建一個新的UniqueConstraint要簡單,但是在有些時候會需要顯示創建UniqueConstraint,例如在需要確保多列合並之后的值為唯一時。
Primarykey
DataTable類允許通過Primarykey屬性為DataTable定義一個主鍵,Primarykey屬性包含的是一個DataColumn對象數組,DataTable使用該數組來構造一個UniqueConstraint,以支持

約束。
ForeignkeyConstraint
外部的約束添加到DataTable中。通常可能不需要顯示創建ForeignkeyConstraint。在DataSet內的兩個DataTable對象之間創建DataRelation也會創建一個ForeignkeyConstraint。


DataRow.RowState屬性
DataSet中的一切都是一種脫機緩存,在DataSet所作的一切修改要是不提交數據庫的話,那么用途也不是很大。那么在DataSet中修改是會有記錄的,這些記錄在DataRow.RowState屬性中,DataRow.RowState使用的是一個枚舉中的值:
Unchanged  該行未包含任何掛起更新
Detached    該行不是DataTable的一個成員
Added         該行已經被添加到了DataTable中,但是不存在在數據庫中
Modified      該行被掛起更改
Deleted       該行為掛起刪除
例子:
Unchanged  row = tb1.NewRow;row["lmf"] = "liumingfeng";
Detached   row.Rows.Add(row);
Added      row = tb1.Rows(0);
Modified   row["lmf"] = "hello world";
Deleted    row.Delete();

一般來說,DataRow有兩個版本,一個是當前的行內容,一個是原來存儲在該行的內容。
可以這樣來查看不同的版本的內容:

row["lmf",DataRowVersion.Current];//當前的值
row["lmf",DataRowVersion.Original];//原來的值

創建DataRelation對象
在創建DataRelation時,應該提供一個名稱,這樣就可以在其集合中查找該對象,並且指定該關系所基於的父列和子列。DataRelation有不同的構造函數來接受單個的DataColumn或者是DataColumn對象數組。最后增加在DataSet中的Relations屬性中,Relations屬性是DataRelation的集合。
用單個的DataColumn創建DataRelation:

//創建數據庫結構
DataSet ds = new DataSet("MyDataSet");
DataTable tb1 = ds.Tables.Add("Customers");
tb1.Columns.Add("CustomerID",typeof(string));
tb1.Columns.Add("CustomerName",typeof(string));

tb1 = ds.Tables.Add("Orders");
tb1.Columns.Add("OrderID",typeof(int));
tb1.Columns.Add("CustomerID",typeof(string));
tb1.Columns.Add("OrderDate",typeof(DateTime));

//添加用單個的DataColumn創建DataRelation
DataRelation rel;
rel = new DataRelation("Customer_Orders",ds.Table["Customers"].Columns["CustomerID"],ds.Table["Orders"].Columns["CustomerID"]);
ds.Relations.Add(rel);

如果希望根據多個字段定義DataRelation,那么就要使用接受DataColumn對象數組的構造函數,代碼示例:

//創建數據庫結構
DataSet ds = new DataSet("MyDataSet");
DataTable tbCustomer = ds.Tables.Add("Customers");
tbCustomer.Columns.Add("CustomerID",typeof(string));
tbCustomer.Columns.Add("CustomerName",typeof(string));

DataTable tbOrder = ds.Tables.Add("Orders");
tbOrder.Columns.Add("OrderID",typeof(int));
tbOrder.Columns.Add("CustomerID",typeof(string));
tbOrder.Columns.Add("CustomerName",typeof(string));
tbOrder.Columns.Add("OrderDate",typeof(DateTime));

//創建引用DataColumn對象的數組
DataColumn[] CustomerP,OrderC;
CustomerP = new DataColumn[]{tbCustomer.Columns["CustomerID"],tbCustomer.Columns["CustomerName"]};
OrderC = new DataColumn[]{tbOrder.Columns["CustomerID"],tbOrder.Columns["CustomerName"]};

//添加用單個的DataColumn創建DataRelation
DataRelation rel;
rel = new DataRelation("Customer_Orders",CustomerP,OrderC);
ds.Relations.Add(rel);

以上的方法都是:先創建一個DataRelation對象,然后再添加到DataSet中的Relations集合中。這個模式和新建的DataTable、DataColumn對象一樣的。
還可以使用語法糖:

ds.Relations.Add("Customer_Orders",ds.Table["Customers"].Columns["CustomerID"],ds.Table["Orders"].Columns["CustomerID"]);

DataRelation對象的用途

DataRelation對象屬於DataSet所有,記錄着DataTable與DataTable的關系,主要的用途是查找有關聯的DataTable中的數據。不過DataRelation不親自處理這個任務,至少不是直接的處理這個任務。這個功能實際上是通過DataRow對象的GetChildRows、GetParentRow和GetParentRows方法提供的。其實在調用這幾個方法時,需要DataRelation對象作為參數傳入,在這幾個方法的內部會引用DataRelation對象來獲取表之間的關系,來查找有關的數據的。

使用GetChildRows方法:

//創建數據庫結構
DataSet ds = new DataSet("MyDataSet");
DataTable tb1 = ds.Tables.Add("Customers");
tb1.Columns.Add("CustomerID",typeof(string));
tb1.Columns.Add("CustomerName",typeof(string));

tb1 = ds.Tables.Add("Orders");
tb1.Columns.Add("OrderID",typeof(int));
tb1.Columns.Add("CustomerID",typeof(string));
tb1.Columns.Add("OrderDate",typeof(DateTime));

//添加用單個的DataColumn創建DataRelation
DataRelation rel;
rel = new DataRelation("Customer_Orders",ds.Table["Customers"].Columns["CustomerID"],ds.Table["Orders"].Columns["CustomerID"]);
ds.Relations.Add(rel);

//填充DataSet
string strConn,strSQL;
......
SqlDataAdapter da = new SqlDataAdapter(strSQL,strConn);
da.TableMapping.Add("Table","Customers");
da.TableMapping.Add("Table1","Orders");
da.Fill(ds);

//遍歷客戶
foreach(DataRow row in ds.Tables["Customers"].Rows)
{
    Console.WriteLine("{0}",row[0]);
    //遍歷相關的訂單,使用GetChildRows方法
    foreach(DataRow rowOrder in row.GetChildRows(rel))
    {
        Console.WriteLine("{0}--{1}",rowOrder["OrderID"],rowOrder["OrderDate"]);
    }
    Console.WriteLine();
}

調用GetChildRows方法的,可將DataRelation對象作為參數傳入,也可以使用DataRelation對象的名稱作為參數傳入。
使用GetParentRow方法:

//遍歷訂單
DataRow coustomer;
foreach(DataRow row in ds.Tables["Orders"].Rows)
{
    //定位相關的父行,查找顧客
    coustomer = row.GetParentRow("Customer_Orders");
}

 

 

 

 

 

 


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM