利用抽象工厂实现自定义多数据类型接口
这几天在看Wrox的VB.NET设计模式高级编程这本书,抽个时间整理一下自己的思维,把以前自己学的东西重新想一想。就是为了模式而模式吧。
1. 抽象工厂模式
GOF的定义:为创建相关联的或与其有依赖关系的对象族提供一个接口(广义接口),而无需为这些对象指定具体的类。
联想到以前用的DAAB的数据类型接口ADOHelper其实就是就是这样的一个接口。在使用的时候首先定义一个AdoHelper对象,再利用多态对其进行赋值。那么我们在使用的过程中接触的始终都是AdoHelper对象,而无须考虑现在是OLEDB的类型还是SQLDB的类型了。
用一个简单的例子说明抽象工厂的工作原理。做一个最简单的支持多数据类型的数据层基类。新建一个类库,自定义一个广义的接口(一个抽象类)命名为DBHelper,简单起见只写一个方法。
Public MustOverride Function ExecuteDataSet(ByVal ConnectionString As String, ByVal CommandText As String) As DataSet
End Class
然后从DBHelper虚拟类下面派生出两个类,OleDB类和SqlDB类,是用以后面对DBHelper赋值的两个对象(定义里面的相关联或与其有依赖关系得对象族也就是他们了)。派生类重写DBHelper的方法(派生类里面的方法要不要重写可以看看虚拟类里面的方法修饰符。)
Imports System.Data.OleDb
Public Class OleDb
Inherits DBHelper
Public Overrides Function ExecuteDataSet(ByVal ConnectionString As String, ByVal CommandText As String) As System.Data.DataSet
Dim Connection As New OleDbConnection(ConnectionString)
Dim Adap As New OleDbDataAdapter(CommandText, Connection)
Dim ds As New DataSet
Connection.Open()
Adap.Fill(ds)
Connection.Close()
Return ds
End Function
End Class
Imports System.Data.SqlClient
Public Class SqlDb
Inherits DBHelper
Public Overrides Function ExecuteDataSet(ByVal ConnectionString As String, ByVal CommandText As String) As System.Data.DataSet
Dim Connection As New SqlConnection(ConnectionString)
Dim Adap As New SqlDataAdapter(CommandText, Connection)
Dim ds As New DataSet
Connection.Open()
Adap.Fill(ds)
Connection.Close()
Return ds
End Function
End Class
然后创建一个新的Web项目做一下测试,在Web项目中添加对刚才那个项目的引用。放两个数据库,一个Access的一个SQL的。
'在此处放置初始化页的用户代码
If Not Page.IsPostBack Then
BindSqlDB()
End If
End Sub
Sub BindOleDB()
Dim Helper As DBHelper
Helper = New OleDb '多态
NewsGrid.DataSource = Helper.ExecuteDataSet(OleDbConnectionString, "select top 10 * from news order by NewsId desc")
NewsGrid.DataBind()
End Sub
Sub BindSqlDB()
Dim helper As DBHelper
helper = New SqlDb '多态
NewsGrid.DataSource = helper.ExecuteDataSet(SqlDbConnectionString, "select top 10 * from news order by NewsId asc")
NewsGrid.DataBind()
End Sub
Public ReadOnly Property OleDbConnectionString() As String
Get
Return "Provider=Microsoft.Jet.OLEDB.4.0;User ID=Admin;Data Source=F:\wwwroot\DAS\DB\**.mdb;"
End Get
End Property
Public ReadOnly Property SqlDbConnectionString() As String
Get
Return "Data Source=**;Initial Catalog=********;User=sa;Pwd=********"
End Get
End Property
最后在Page_Load事件里面把自己想要运行的数据库类型放里面就可以执行了。同时使用两个不同的对象却通过同一个对象Helper获取这就是我们想要实现的目的。显然一两个方法体现不出该模式的优越性。实际使用的情况要比这复杂的多了...