天天看點

第三十一講 : DataSet和DataAdapter(上)

主要内容:

    1. DataSet和DataAdapter簡介

        1. DataAdapter用于從資料源檢索資料并填充

        2. DataSet中的表。DataAdapter還可将DataSet所做更改解析回資料源

        執行個體:

        {

            string constr = "server=root-pc; database=hrms; uid=sa; pwd=' 000000'";

            SqlConnection conn = new SqlConnection(constr);

            string sql = "select bh as 員工編号,xm as 姓名,xb from employee";

            SqlDataAdapter sda = new SqlDataAdapter(sql, conn);

            DataSet ds = new DataSet();

            sda.Fill(ds);

            dataGridView1.DataSource = ds.Tables[0];

        }

    2. 填充多張表到DataSet

        SqlDataAdapter類有四個重載

            SelecteCommand屬性

            SelecteSqlconnection屬性

        dataGridView控件的使用

            行:Rows

            列:Cells

        填充表是使用DataAdapter對象的fill方法

        DataSet是一個表的集合,可以存儲多張表

        如:

        SqlDataAdapter sda = new SqlDataAdapter(sql, conn);

            DataSet ds = new DataSet();

            sda.Fill(ds);

        fill方法就是将通過連接配接對象和指令對象擷取的資料填充到DataSet對象中去。然後再通過DataSet對象中的表集合屬性讀取表中的資料。

        如:

        dataGridView1.DataSource = ds.Tables[0];

    3. DataSet資料表與關系

        DataSet多張表的表名存在大小寫區分

        DataTable對象 和 DataRelation對象

        DataTable是建立表的類

        如:

        DataTable tbl=new DataTable("users")

        即建立了一個表名為users的表

        表有行集和列集組成,是以通過tbl對象就可以調用Rows和Columns兩上集合,并從中讀取資料。

        DataRow 和 DataColumn是定義表的行和列變量兩個資料類型。

        如:

        //建立表,并為此表添加列

        DataTable dt2 = ds3.Tables.Add("NewTable2");

        DataColumn col2 = dt2.Columns.Add("ID",typeof(int));//添加列

        //定義列屬性

        col2.AllowDBNull = false;//值不能為空

        //col2.MaxLength = 10;//最大長度10

        col2.Unique = true;//值的唯一性為真

        //為表定義一個主鍵限制

        dt2.PrimaryKey = new DataColumn[] { dt2.Columns["ID"] };

        //添加一列

        DataColumn col3 = dt2.Columns.Add("xm",typeof(int));

        col3.AutoIncrement = true;//定義列的自增長屬性為真

        col3.AutoIncrementSeed = 1;//自增長的種子為1

        col3.AutoIncrementStep = 1;//增長的步幅為1

        col3.ReadOnly = true;//定義此列為隻讀屬性

        //再加一列

        DataColumn col4 = dt2.Columns.Add("sum",typeof(int),"ID*xm");

        //======================================================

        //往表中添加行

        DataRow r1 = ds3.Tables["NewTable2"].NewRow();

        r1[0] = 100;//為行的第一列指派

        object[] z = { 100};//定義object對象集合,存儲行中的各列的值

        ds3.Tables["NewTable2"].LoadDataRow(z, false);

        label3.Text = dt2.Rows[0][dt2.Columns[0]].ToString();

        label3.Text += "\n"+dt2.Rows[0][dt2.Columns[1]].ToString();

        label3.Text += "\n" + dt2.Rows[0][dt2.Columns[2]].ToString();

        注意:也可以以執行個體化的式建立行和列

        如:

        DataCloumn col=new DataCloumn();

        DataRow row=table.NewRow();//建立行需要使用表的NewRow()方法

        //為列指定資料類型

        col.DataType=System.Type.GetType("System.Int32");

        col.ColumnName="Hello";//定義列名屬性

        //建立表間關系

        使用DataRelation對象

        DataRelation relation=new DataRelation(限制名,父表主鍵,子表主鍵);

        //将這個關系再添加到子表中去

        ds.Tables["子表名"].ParentRelations.Add(relation);

        //擷取dataGridView對象中某單元格的值

        dataGridView.CurrentRow.Cells[0].value

        CurrentRow:目前行屬性

        Cells:控件的列集合

        //支援排序,篩選,搜尋的DataView類

        DataView dv=ds.Tables["表名"].DefaultView;

        //設定搜尋條件

        dv.RowFilter="表中的列名="+條件值

        //指定到資料源

        dataGridView.DataSource=dv;

    4. 關系與限制

    5. 向DataSet中的表添加限制

比着老師的例子,完完整整的敲了一遍代碼,争取了解每一行代碼的含義,唯一搞不清楚的就是列屬性的ColumnName和Caption,百度了一下,說的也是不清不楚的,但最重要的是不影響建表和操作。

如果我把一個的字段屬性ColumnName="a", Caption="A",在測試中列标題顯示的是a. 如果說Caption這個屬性是給客戶看的,但是為啥列标題顯示的是表字段名呢?我試着設定row["A"]="test"時,提示是A是不是屬于表的屬性,就是隻能通過ColumnName屬性對表字段進行指派。一頭霧水!

原代碼如下:

using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Windows.Forms;
using System.Data.SqlClient;

namespace WF31
{
    public partial class Form1 : Form
    {
        public Form1()
        {
            InitializeComponent();
        }

        //資料庫連接配接字元串
        string strConn = "server=.; database=hrms; uid=sa; pwd=123123;";
        //資料檢索指令
        string sqlSelect = "select bh,xm,xb,dz,bm from employee";

        DataSet ds;//建立一個資料集對象引用

        /// <summary>
        /// 視窗加載
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="e"></param>
        private void Form1_Load(object sender, EventArgs e)
        {
            using (SqlConnection conn = new SqlConnection(strConn))
            {
                SqlCommand cmd = new SqlCommand(sqlSelect, conn);
                cmd.CommandType = CommandType.Text;
                SqlDataAdapter sda = new SqlDataAdapter();//建立一個資料擴充卡
                ds = new DataSet();//建立一個資料集對象,預設資料集包含一個空表
                sda.SelectCommand = cmd;//設定資料擴充卡的檢索指令對象的屬性
                sda.Fill(ds);//使用資料擴充卡的Fill方填充資料到資料集的預設表中
                //以下是綁定資料到DataGridView控件,隻能以表資料方式進行
                //由于資料集中包含一個預設空表,且隻有一個表,在不知道表名的情況下,使用
                //DataSet資料集的表集合中索引,如下
                dataGridView1.DataSource = ds.Tables[0];//綁定資料表到控件

            }
        }

        /// <summary>
        /// 建立表
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="e"></param>
        private void button1_Click(object sender, EventArgs e)
        {
            DataTable table = new DataTable("Parent");//建立一個表對象,并初始化表名屬性
            DataColumn column;//定義一個列引用
            DataRow row;//定義一個行引用

            column = new DataColumn();//建立一個表的列對象
            //設定列的資料類型
            column.DataType = System.Type.GetType("System.Int32");//第一列資料類型為整型
            //設定列的名稱
            column.ColumnName = "id";//這個名稱為字段名稱
            //指定列的讀取方式
            column.ReadOnly = true;//指定為隻讀
            //列中的值是否為唯一值
            column.Unique = true;
            //設定列的标題
            column.Caption = "ParentId";
            //将此列添加到表的列集合中
            table.Columns.Add(column);

            //再建立一個列
            column = new DataColumn();//初始化列對象
            //設定列是否為自增列
            column.ColumnName="item";
            column.DataType=System.Type.GetType("System.String");
            column.AutoIncrement = false;
            column.Caption = "ParentItem";
            column.ReadOnly = false;
            column.Unique = false;
            table.Columns.Add(column);


            //設定表的主鍵,以集合的方式建立,意思就是可以通過此方式為表建立組合鍵
            DataColumn[] PrimaryKeyColumns = new DataColumn[1];//隻包含一個主鍵列
            //指定主鍵列
            PrimaryKeyColumns[0] = table.Columns["id"];//指定字段id為此表的主鍵
            //再将主鍵綁定到表中
            table.PrimaryKey = PrimaryKeyColumns;

            

            //為上表添加資料記錄,即行資料
            //老師強調了,這個行記錄對象不能像列對象一個進行new DataRow;
            //而是使用上面的已經執行個體化好了的Table架構進行執行個體化
            row = table.NewRow();//使用現有的表架構來執行個體化行對象
            //為建立的行對象中的每一列指派
            row["id"] = 1;
            row["item"] = "父表第一行資料";
            //将生成的行添加到表的行集合
            table.Rows.Add(row);


            //再加一行
            row = table.NewRow();
            row["id"] = 2;
            row["item"] = "父表第二行資料";
            //将生成的行添加到表的行集合
            table.Rows.Add(row);

            //再加一行
            row = table.NewRow();
            row["id"] = 3;
            row["item"] = "父表第三行資料";
            //将生成的行添加到表的行集合
            table.Rows.Add(row);

            //建立一個資料集對象
            ds = new DataSet();//初始化資料集對象
            //将表添加到資料集的表集合中
            ds.Tables.Add(table);

            //************父子表的分隔線*********************

            //接下來是建立一個子表
            table = new DataTable("Child");

            //初始化列對象
            column = new DataColumn();
            column.ColumnName = "id";
            column.DataType = System.Type.GetType("System.Int32");
            column.Caption = "ChildId";
            column.AutoIncrement = true;
            column.ReadOnly = true;
            column.Unique = true;

            table.Columns.Add(column);

            column = new DataColumn();
            column.ColumnName = "childItem";
            column.Caption = "ChildItem";
            column.DataType = System.Type.GetType("System.String");
            column.AutoIncrement = false;
            column.ReadOnly = false;
            column.Unique = false;

            table.Columns.Add(column);

            //再組建一列作為主副間的關系列
            column = new DataColumn();
            column.ColumnName = "parentId";
            column.Caption = "ParentId";
            column.DataType = System.Type.GetType("System.Int32");
            column.AutoIncrement = false;
            column.ReadOnly = false;
            column.Unique = false;
            column.AllowDBNull = false;

            table.Columns.Add(column);

            

            //為子表添加資料
            

            for (int i = 0; i < 5; i++)
            {
                row = table.NewRow();
                row["childItem"] = "子表項資料第" + i + "号";
                row["parentId"] = 1;
                table.Rows.Add(row);
            }

            

            for (int i = 5; i < 11; i++)
            {
                row = table.NewRow();
                row["childItem"] = "子表項資料第" + i + "号";
                row["parentId"] = 2;
                table.Rows.Add(row);
            }

            

            for (int i = 11; i < 15; i++)
            {
                row = table.NewRow();
                row["childItem"] = "子表項資料第" + i + "号";
                row["parentId"] = 3;
                table.Rows.Add(row);
            }

            //也将此表添加到資料集中,因為在建立表的同時初始了表名屬性,可以以表名來指定表對象
            ds.Tables.Add(table);

            //最後是建立表間的關系
            //先擷取父表的關系列
            DataColumn PrimaryColumn = ds.Tables["Parent"].Columns["id"];

            //擷取副表的關系列
            DataColumn ChildColumn = ds.Tables["Child"].Columns["parentId"];

            //建立表間關系
            //關系類構造函數的三個參數:1.限制名,2.父表關系字段,3.子表關系字段
            DataRelation relation = new DataRelation("PCrelation", PrimaryColumn, ChildColumn);

            //将限制關系添加到子表中
            ds.Tables["Child"].ParentRelations.Add(relation);//注意子表的父關系也是一個集合

            if (ds.Tables.Count == 2)
            {
                MessageBox.Show("父表:" + ds.Tables["Parent"] + " 建立成功!\n子表:" + ds.Tables["Child"] + " 建立成功!");
            }
            else {
                MessageBox.Show("建立失敗!");
            }

        }

        /// <summary>
        /// 綁定手工建立的表到控件
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="e"></param>
        private void button2_Click(object sender, EventArgs e)
        {
            dgvParent.DataSource = ds.Tables["Parent"];
            dgvChild.DataSource = ds.Tables["Child"];
        }

        private void dgvParent_CellClick(object sender, DataGridViewCellEventArgs e)
        {
            //先擷取使用者的選中行的主鍵
            string pid = dgvParent.CurrentRow.Cells[0].Value.ToString();

            //建立資料視圖對象
            DataView dv = new DataView();
            dv = ds.Tables["Child"].DefaultView;
            dv.RowFilter = "parentId=" + Convert.ToInt32(pid);
            dgvChild.DataSource = null;
            dgvChild.DataSource = dv;
        }

    }
}
           

測試結果:(我的測試結果大多為gif小動畫,但有的去浏覽時不動,很大可能是伺服器被屏蔽,因為系統在沒有任何發動的情況下有時候是好的,可以另存為到本地看看。)

第三十一講 : DataSet和DataAdapter(上)