关键词:作者罗姗
众所周知,VB.NET自身并不具备对数据库进行操作的功能,它对数据库的处理是通过.NET FrameWork SDK中面向数据库编程的类库和微软的MDAC来实现的。其中,ADO.NET又是.NET FrameWork SDK中重要的组成部分。要了解VB.NET的数据库编程,首先要明白ADO.NET的工作原理以及相关的对象、方法、属性。本文将结合具体实例为你简单介绍ADO.NET数据库访问对象以及VB.NET数据库编程基本方法。
一、ADO.NET数据库访问对象
(一)ADO.NET简介
ADO.NET是由微软Microsoft ActiveX Data Object(ADO)升级发展而来的。是在.NET中创建分布式数据共享程序的开发接口。ADO.NET的数据存取API提供两种数据访问方式,分别用来识别并处理两种类型的数据源,即sql Server7.0(及更高的版本)和可以通过OLE DB进行访问的其他数据源。为此ADO.NET中包含了两个类库,System.Data.sql库可以直接连接到sql Server的数据,System.Data.ADO库可以用于其他通过OLE DB进行访问的数据源。如Access数据。
(二)ADO.NET的名称空间
ADO.NET是围绕System.Data基本名称空间设计,其他名称空间都是从System.Data派生而来。它们使得ADO.NET不仅访问DataBase中的数据,而且可以访问支持OLE DB的数据源。
当我们讨论ADO.NET时,实际讨论的是System.Data和System.Data.OleDb名称空间。这两个空间的所有类几乎都可以支持所有类型的数据源中的数据。这里我们讨论与后文实例有关的类。即OleDbconnection、OleDbDataAdapter、DataSet和DataView。
上面列举的类中没有OleDb前缀的,派生自System.Data空间,有此前缀的派生自System.Data.OleDb空间。在使用中,如果要引用OleDb前缀的类,必须导入System.Data.OleDb名称空间。语法如下:
Imports System.Data.OleDb
使用没有此前缀的类必须导入System.Data名称空间。语法如下:
Imports System.Data
1.OleDbConnection类
OleDbConnection类提供了一个数据源连接。这个类的构造函数接受一个可选参数,称为连接字符串。
(1)连接字符串:
连接字符串本身由下表中列出的参数构成。(
图)
我们来看一下如何在连接字符串上使用参数来初始化一个连接对象。
Dim objconnecttion as OleDbConnection=New OleDbConnection(″Provider=sqlOLEDB;″&″DataSource=localhost;Initial Catalog=pubs;″&″UserID=liuguo;Password=1234;″)
上面的连接字符串使用sqlOLEDB提供者访问sql Server数据库。Data Source参数指定数据库位于本地机器上,Initial Catalog参数表示我们要访问的数据库名称是“pubs”。
打开数据库:objConnection.Open()
2.OleDbDataAdapter类
OleDbDataAdapter类可以在所有OLE DB数据源中读写数据,并且可以设置为包含要执行的sql语句或者存储过程名。OleDbDataAdapter类并不真正存储任何数据,而是作为DataSet类和数据库之间的桥梁。
(1)SelectCommand属性:
(2)Fill方法:
Fill(DataSet,String)
其中,DataSet参数用于指定一个有效的DataSet对象,将用数据进行填充;String参数指定了用于表映射的表名称。
(3)DataView类:
DataView类一般用于从DataSet类中排序、过滤、查找、编辑和导航数据。与DataSet一样其内部数据使用的是DataTable对象。DataView类是DataTable对象的一个自定义视图。同时DataView中的数据又独立于DataSet中DataTable包含的数据,所以可以对数据进行操作而又不会影响DataSet中的数据。其主要方法与属性如下:
Sort方法:对DataView包含的数据进行排序。语法如下:
objDataView.Sort = ″排序条件″
rec=objDataView.Find(″指定条件″)
(三)ADO.NET的核心组件
ADO.NET的核心组件主要包括:
Connections:连接管理数据库事务。
Commands:向数据库发送的操作命令。
DataReaders:直接读取流数据。
DataSets和DataSetCommands:处理内存镜像数据。
ADO.NET首先用Connections对象在Web页面和数据库之间建立连接,然后通过Commands向数据库提供者发出操作命令,使操作结果以流数据的形式返回连接。再通过DataReaders快速读取流数据,保存数据到DataSets对象。最后再由DataSetCommands对象对数据进行集中访问和操作。
1.Connections对象
.NET框架中共提供了两个Connections对象:sqlConnection和ADOConnection。应用Connections对象时,先用Connections对象建立连接,然后调用Open方法来打开连接。通常建立链接时,要提供一些信息,如数据库所在位置、数据库名称、用户账号、密码等相关信息,Connection对象提供了一些常用属性用来进行此类设置。
Dim myConnection as string = ″server=localhost;uid=liuguo;pwd=12345;database=northwind″
Dim myConn As OleDbConnection = New OleDbConnection(myConnection)
ADOConnection的具体操作方法是:
Dim myConnection As string = ″localhost;uid=liuguo;pwd=12345;Intial catalog=Northwind;″
Dim myConn As OleDbConnetion = New OleDbConnection(myConnection)
MyConn.Open()
2.Commands对象
当链接到数据库之后,可以使用Command对象对数据库进行操作,如进行数据添加、删除、修改等操作。一个命令(Command)可以用典型的SQL语句来表达,包括执行选择查询(Select Query)来返回记录集,执行行动查询(Action Query)来更新(增加、编辑或删除)数据库的记录,或者创建并修改数据库的表结构。当然命令(Command)也可以传递参数并返回值。Command可以被明确的界定,或者调用数据库中的存储过程。
Dim objCmd as New OleDbCommand(″SELECT * From users″,objConn)
以上语句建立Command,根据习惯,也可以使用以下方法:
Dim objCmd as New OleDbCommand()
objCmd.Connection = objConn
objCmd.CommandText = ″SELECT * FROM users″
3.DataReaders对象
DataReaders是专门用来读取数据的对象,这个对象除了读数据以外,不能做其他任何数据库操作。
Dim objReader as OleDbDataReader
objReader = objCmd.ExecuteReader
While objReader.Read
Response.Write(objReader.GetString(0) & ″
″=
″=
End While
4.DataSet对象
DataSet是ADO.NET的核心。DataSet是一个存在于内存中的数据库,也就是说它是离线的,并没有同数据库建立即时的连线。在ADO.NET中,DataSet是专门用来处理从数据保存体(Data Store)中读出的数据。不管底层的数据库是SQL Server还是ADO,DataSet的行为都是一致的。可以使用相同的方式来操作从不同数据来源取得的数据。
在DataSet中可以包含任意数量的DataTable(数据表),且每个DataTable对应一个数据库的数据表(Table)或视图(View)。一般来说,一个对应DataTable对象的数据表就是一堆数据行(DataRow)与列(DataColumn)的集合。DataTable会负责维护每一笔数据行保留它的初始状态(Original State)和当前的状态(Current State),以解决多人同时修改数据时引发的冲突问题。
DataSet是XML与ADO结合的产物,它的一个重要的特点是与数据库或SQL无关。它只是简单地对数据表进行操作,交换数据或是将数据绑定到用户界面上。
如以下这个例子:
Dim ds1 As New DataSet()
Dim dtable As new DataTable(″people″)
With dtable.Columns
.Add(″FName″,System.Type.GetType(″System.String″))
.Add(″LName″,serif; line-height:24px">
.Add(″UID″,System.Type.GetType(″System.Int32″))
End With
dtable.Columns(″UID″).AutoIncrement = True
ds1.Tables.Add(dtable)
dim pkey() as DataColumn = {ds1.Tables(″people″).Columns(″UID″)}
ds1.Tables(″people″).PrimaryKey = pkey
以上语句稍微有点复杂,我们来简单分析一下。
前半部分我们建立了一个DataSet和一个叫People的DataTable,然后,我们为这个DataTable加入了三个列并将“UID”列设为自动递增。最后,将这个DataTable加入到了DataSet。最后我们定义一个叫pkey()的主键,将其指向People。
二、数据的绑定
VB.NET没有自己的类库,它依托的是.NET FrameWork SDK中的类库,虽然在.NET FrameWrok SDK中并没有提供在VB中的的DbLabel、DbComboBox等数据库组件,但.NET FrameWork SDK中提供了一种数据绑定技术,可以把打开的数据表中的某个或者某些字段绑定到在命名空间System.Window.Forms中定义的WinForm组件(如TextBox组件、ComboBox组件、Label组件等)中的某些属性上,从而提供这些组件显示出数据表中的记录信息,也就实现了DbTextBox、DbComboBox等组件。
(一)数据绑定和Windows窗体基础知识
数据绑定指的是一个过程,即在运行时自动为包含数据的结构中的一个或多个窗体控件设置属性的过程。具体而言,是指Windows窗体使用ADO.NET进行数据绑定的过程。使用数据绑定,你无需显式编写实例化连接和创建数据集的代码(而使用非绑定窗体则必须这样做),与Windows窗体相关联的向导将为你编写必要的ADO.NET代码。
Windows窗体使用户可以轻松绑定到几乎所有包含数据的结构。这表示用户可以使用ADO.NET绑定到传统的数据存储区(如存储在Access或SQL Server表中的数据),也可以绑定到从文件读取的、包含在其他控件的或存储在阵列中的数据结果。将窗体绑定到数据后,就可以将窗体上的控件绑定到特定的数据元素。最传统的数据绑定包括将文本框控件(TextBox)的Text属性绑定到数据源的列,还可以绑定Image控件的图形、控件的背景或窗体上任意控件的其他任意属性。
Windows窗体可以进行两种类型的数据绑定:简单数据绑定允许将控件绑定到单个数据元素;复杂数据绑定允许将多个数据元素绑定到一个控件。
(二)数据与控件的绑定
在VB.NET中要向控件绑定一个数据源,就必须为该控件设置DataBinding属性。该属性可以访问ControlBindingsCollection类,该类对每一个控件的绑定进行管理,并且具有很多属性和方法。
Add方法为控件创建一个绑定并将它加到ControlBindingsCollection中。Add方法有3个参数语法如下:
Object.DataBindings.Add(propertyname,datasource,datamember)
其中,Object表示窗体上的有效控件;Propertyname参数表示被绑定控件的属性;Datasource参数表示被绑定的数据源,可以是任何包含数据的有效对象如DataSet,DataView或者DataTable等;Datamember参数代表被绑定给控件的数据源中的数据字段。
1.绑定前的准备工作
(1)创建一个名为db1的Access数据库,数据表Student的结构如
图所示:
(2)创建和配置数据集:
创建项目,就可以创建和配置窗体所基于的数据集了。数据集是内存中包含表、关系和约束的缓存,其中的每个表均为列和行的集合。数据集能够识别其原始状态和当前状态,因此可以跟踪发生的变化。数据集中的数据被视为可更新数据。步骤如下:
在表单中增加一个OleDbDataAdapter控件。这时会自动弹出“数据适配器配置向导”对话框。点击“下一步”选择“新建连接”将弹出相应的对话框,选择“Microsoft Jet 4.0 OLE DB Provider”选项,点击“Next”按钮,设定数据源。在这里设置好你的数据源后点击“OK”按钮。
SELECT StuID,StuName,StuSex,StuBorn,StuCore FROM student
在窗体的组件栏中将显示名为OleDbConnection1的OleDbConnection对象和名为OleDbDataAdapter1的OleDbDataAdapter对象。其中,OleDbConnection1对象包含有关如何访问选定数据库的信息。OleDbDataAdapter1对象包含一个查询,它定义了要访问的数据库中的表和列。
(3)生成数据集类:
点击“数据→生成数据集”菜单命令,此时将出现“生成数据库”对话框。在“新建”框中myDataSet作为要创建的新数据集的名称。确保选中“将此数据集添加到设计器”选项。点击 “确定”按钮。这样即可生成数据集。
到此,准备工作结束。我们就可以将数据集绑定给控件来显示数据集中所包含的数据了。
2.绑定到DataGrid控件
完成上述步骤,即将数据集绑定到数据网格控件中了。只需再完成一个步骤,就可以看到数据网格控件中显示的数据了。
Private Sub frmtest_Load( ByVal sender As System.Object,_
ByVal e As System.EventArgs) Handles MyBase.Load
'加载数据网格控件
MyDataSet1.Clear()
OleDbDataAdapter1.Fill(mydataset1,″student″)
End Sub
在Load事件过程中,首先需要清除数据集,然后用先前创建的OleDbDataAdapter1对象的Fill方法填充数据集。需要将表名传递给第二个参数,因为数据网格控件将使用第二个参数检索以前在DataMember属性中指定的正确DataMember (student)。
(3)现在,我们可以来看看我们的成果了,试运行一下程序。
在“解决方案资源管理器”窗口中,右击项目名称,从快捷菜单中选择“属性”命令,在打开的对话框中点击“启动对象”组合框并从列表中选择“frmtest”选项。然后点击“确定”按钮。最后按下F5键即可运行此项目。
3.绑定到TextBox控件
界面创建完成以后,我们就可以把数据集绑定到每个TextBox控件上了。步骤如下:
(2)打开组合框并将各个文本框绑定到相应的字段。如需要将“TxtStuID”文本框绑定到StuID字段,请点击myDataSet1上的“+”号,再点击 student上的“+”号,然后选择StuID字段。
(3)按照上述方法把其他几个文本框绑定到相应的字段上。
Private Sub frmtest_Load(ByVal sender As System.Object,ByVal e As System.EventArgs) Handles MyBase.Load
OleDbDataAdapter1.Fill(MyDataSet1,serif; line-height:24px">
按下F5键试运行一下程序。仔细观察一下运行结果我们就会发现,程序在实现时自动用数据集中的第一条记录来填充各件控件。
(三)用代码实现数据绑定
为了便于更好的理解,我们仍然选用“TextBox”控件作为实例来介绍。
1.绑定到TextBox控件
(1)界面设计:
(2)代码实现:
Imports System.Drawing
Imports System.Windows.Forms
Imports System.ComponentModel
Imports System
Public Class Form1
Inherits Form
Private WithEvents Button1 As Button
Private myDataSet As DataSet
Private components As System.ComponentModel.Container
Public Sub New()
MyBase.New()
GetConnected() '这个过程是用于建立连接,打开数据库
InitializeComponent()
'清除在程序中使用过的资源
Protected Overloads Overrides Sub Dispose(ByVal disposing As Boolean)
'
Public Sub GetConnected()
'创建一个 OleDbConnection
Dim ConnectionString As String = ″ Provider = Microsoft.Jet.OLEDB.4.0; Data Source = e:\My Documents\db1.mdb″
Dim myConn As OleDbConnection = New OleDbConnection()
myConn.ConnectionString = ConnectionString
Dim strCom As String = ″ SELECT * FROM student ″
'创建一个 DataSet
myDataSet = New DataSet()
myConn.Open()
'用 OleDbDataAdapter 得到一个数据集
Dim myCommand As OleDbDataAdapter = New OleDbDataAdapter(strCom,myConn)
'把Dataset绑定student数据表
myCommand.Fill(myDataSet,serif; line-height:24px">
'关闭此OleDbConnection
myConn.Close()
'初始化窗体中的组件
Private Sub InitializeComponent()
'将各个文本框控件绑定到数据库的各个字段。
Private Sub Button1_Click(ByVal sender As Object,serif; line-height:24px">
ByVal e As System.EventArgs) Handles Button1.Click
TxtStuID.DataBindings.Add(New Binding(″Text″,Me.myDataSet,″student.StuID″))
TxtStuName.DataBindings.Add(New Binding(″Text″,″student.StuName″))
TxtStuSex.DataBindings.Add(New Binding(″Text″,″student.StuSex″))
TxtStuBorn.DataBindings.Add(New Binding(″Text″,″student.StuBorn″))
TxtStuCore.DataBindings.Add(New Binding(″Text″,″student.StuCore″))
End Class
Module Module1
Sub Main()
Application.Run(New Form1())
End SubEnd Module
编译后运行程序,看看是不是与上面介绍的实例运行结果相同。
在上面的代码中,我们新建了一个GetConnected()过程,用于建立连接,打开数据库。在用代码实现数据绑定或者对数据库进行任何操作前,就必须要先建立连接,打开数据库,程序运行结束后再关闭数据连接。
在Button1_Click过程中,我们把“TextBox”控件绑定到数据集myDataSet中“student”的各个字段上。
2.绑定到Label控件
有了上面的内容做基础,再来讨论如何把数据集绑定到Label控件上就显得很简单了。把数据绑定到Label控件的方法与绑定到TextBox控件的方法大同小异。此处不再详细讲解,只给出代码实现绑定到Label控件的核心部分代码。
Private Sub Button1_Click (ByVal sender As Object,serif; line-height:24px">
ByVal e As System.EventArgs ) Handles Button1.Click
'把student表的StuName字段绑定到Label1的Text属性上。
Label1.DataBindings.Add ( New Binding ( ″Text″,″student.StuName″ ) )
3.绑定到ComboBox控件
上面介绍的是对组件的简单数据绑定,对组件的复杂数据绑定和它有所区别,也有所相同,具体如下:
(2)实现数据绑定:
设定了ComboBox组件的三个属性就可以实现数据绑定了,这三个属性是“DataSource”、“DisplayMember”、“ValueMember”。其中DataSource表示指定的数据集;DisplayMember表示ComboBox组件显示的字段值;ValueMember表示ComboBox组件选择后的值。这三个属性的具体使用方法如下:
ComboBox1.DataSource = Me.myDataSet
ComboBox1.DisplayMember = ″studnet.StuName″
ComboBox1.ValueMember = ″ studnet.StuName ″
Private Sub Button1_Click ( ByVal sender As Object,serif; line-height:24px">
ComboBox1.DisplayMember = ″student.StuName″
ComboBox1.ValueMember = ″ student.StuName ″
三、数据库简单操作
前面介绍了ADO.NET基础,以及ADO.NET与Windows窗体控件的绑定方法。但是,对于数据库编程我们更想了解的还是如何增加记录,删除记录,更新记录等数据库记录的操作方法。这里我们将以一个具体的实例为大家介绍这些操作方法。
'打开数据库
Public Sub OpenData()
'绑定数据到TextBox控件
txtStuID.DataBindings.Add(New Binding(″Text″,serif; line-height:24px">
txtStuName.DataBindings.Add(New Binding(″Text″,serif; line-height:24px">
txtStuSex.DataBindings.Add(New Binding(″Text″,serif; line-height:24px">
txtStuBorn.DataBindings.Add(New Binding(″Text″,serif; line-height:24px">
txtStuCore.DataBindings.Add(New Binding(″Text″,serif; line-height:24px">
完成以上步骤后,我们就可以通过编程对数据库进行各作操作了。
1.实现对数据记录的浏览
在完成对窗体中的WinForm组件进行绑定后,实现对数据记录的浏览操作的关键就是要找到如何定位数据记录指针的方法。而要实现这种处理就需要用到.NET FrameWork SDK中的名称空间System.Windows.Froms中的BindingManagerBase类。
BindingManagerBase是一个抽象的类,主要用于管理同一数据表所有绑定对象。BindingManagerBase类中定义了二个属性“position”和“Count”,第一个属性是定义当前数据指针,而第二个属性主要是得到当前数据集有多少记录数目。在已经进行完数据绑定后,通过这两个属性配合使用,实现对数据记录的浏览。
(1)向上翻阅一条记录:
Private Sub btnPrevIoUs_Click(ByVal sender As System.Object,ByVal e As System.EventArgs) Handles btnPrevIoUs_.Click
Me.BindingContext(myDataSet,″student″).Position -= 1
(2)向下翻阅一条记录:
Private Sub btnNext_Click(ByVal sender As System.Object,ByVal e As System.EventArgs) HandlesbtnNext.Click
(3)翻到最后一条记录:
Private Sub btnEnd_Click(ByVal sender As System.Object,ByVal e As System.EventArgs) Handles btnEnd.Click
(4)翻阅到第一条记录:
Private Sub btnFirst_Click(ByVal sender As System.Object,ByVal e As System.EventArgs) Handles btnFirst.Click
说明:为了代码书写方便,我们可以先定义一个BindingManagerBase对象myBind,如myBind = Me.BindingContext (myDataSet,″student″ ),于是以上各句代码均可以简写成:
向上翻阅一条记录:myBind.Position = myBind.Position - 1
向下翻阅一条记录:myBind.Position = myBind.Position + 1
翻阅到最后一条记录:myBind.Position=myBind.count - 1
翻阅到第一条记录:myBind.Position = 0
2.删除数据记录
Private Sub btnDel_Click(ByVal sender As System.Object,ByVal e As System.EventArgs) Handles btnDel.Click
Dim strDele As String = ″DELETE From student WHERE StuID = '″ + txtStuID.Text + ″ '″
Dim myCommand As OleDbCommand = New OleDbCommand(strDele,serif; line-height:24px">
myCommand.ExecuteNonQuery() myDataSet.Tables(″student″).Rows(Me.BindingContext(myDataSet,″student″).Position).Delete()
myDataSet.Tables(″student″).AcceptChanges()
10.myConn.Close()
前面四行代码我们已经非常熟悉,目的是建立与数据据的连接并打开数据库。第6行代码我们建立一个SQL查询,用来查询数据表中StuID字段值等于TxtStuID.Text输入值的所有记录。并在第7行代码中将查询结果建立一个新的OleDbCommand对象,用来指定要删除的记录。第8行代码是从数据库中删除指定的记录,第9行代码是从myDataSet中删除记录。前者是物理上删除记录,如果去掉第8行代码运行程序你就会发现,记录只是在当前操作中被删除了,在数据库中依然存在。
其中第6行代码中定义的SQL查询条件读者可以根据需要自行指定。需要说明的是,由于我们在创建数据表时,指定StuID字段的类型为Text类型,因此在书写sql语名时要在“=”号前加上单引号,具体格式请参照第6行代码。如果StuID字段类型为数字型,那么第6行正确写法应该为:
Dim strDele As String = ″DELETE From student WHERE StuID = ″ + txtStuID.Text
3.修改数据记录
'以上代码用来连接数据源
myDataSet.Tables(″student″).Rows(Me.BindingContext(myDataSet,″student″).Position).BeginEdit()
'利用sql语句创建数据更新集合
Dim StrUpdate As String = ″Update student SET StuName='″ + txtStuName.Text + ″',StuSex='″ + txtStuSex.Text + ″',StuBorn='″ + txtStuBorn.Text + ″',StuCore='″ + txtStuCore.Text + ″' WHERE StuID='″ + txtStuID.Text + ″'″
'利用sql结果创建新的OleDbCommand对象
Dim myCommand As OleDbCommand = New OleDbCommand(StrUpdate,serif; line-height:24px">
myCommand.ExecuteNonQuery()
上述代码中我们采用sql语言中的Update语名来更新记录,对各个TextBox中的值修改后更新到数据库。其中重要语句就是sql语句的编写。如果你有不明白的地方,请参阅sql相关资料。代码中我们同时还利用了BeginEdit()与EndEdit()方法,任何从数据的修改都必须在这两个方法之间进行。前者是数据修改的入口,后者则是完成将数据写入数据库的工作。
4.增加数据记录
增加数据记录与修改数据在实现方法上有很多相同之处。在下面的实例中我们利用sql的Insert语句在指定位置插入一条记录,把更新到数据库。如果你想在数据表最后增加一条记录,只需要将数据记录指针指向数据表末尾就行了。
Private Sub btnAdd_Click(ByVal sender As System.Object,ByVal e As System.EventArgs) Handles btnAdd.Click
Dim StrAdd As String = ″insert into student (Stuid,StuCore) values('″ + txtStuID.Text + ″','″ + txtStuName.Text + ″','″ + txtStuSex.Text + ″','″ + txtStuBorn.Text + ″','″ + txtStuCore.Text + ″')″
Debug.Write(StrAdd)
End Sub
完成上述设计后我们来看看整个程序的运行结果。按下F5键运行程序即可。
本文中所有代码均在Windows XP+VB.NET环境下调试通过。