先来段起始源码:
需求是: 使用SQLServer数据库,对表User进行Insert和GetUser两个操作
using System; using System.Collections.Generic; using System.Linq; using System.Text; using System.Threading.Tasks; namespace ConsoleApplication2 { class Program { static void Main(string[] args) { SqlserverUser sql = new SqlserverUser(); sql.Insert(new User() { ID = 1, Name = "张三" }); sql.GetUser(1); Console.ReadKey(); } } public class User { public int ID { get; set; } public string Name { get; set; } } public class SqlserverUser { public void Insert(User user) { Console.WriteLine("SQL Server给User表插入一条记录"); } public User GetUser(int id) { Console.WriteLine("SQL Server根据ID得到User表一条记录"); return null; } } }
然后客户改了需求了。
要求即可以使用SQLServer,也可以使用Access数据库。
下面是勇哥实现的简单类工厂方式。
类图如下:
源码如下:
using System; using System.Collections.Generic; using System.Linq; using System.Text; using System.Threading.Tasks; namespace ConsoleApplication17 { class Program { static void Main(string[] args) { UserOperateFac fac = new UserOperateFac(); var obj= fac.GetObj(UserOperEnum.Access); obj.Insert(new User() { ID=1, Name="张三" }); var s1= obj.GetUser(1); Console.ReadKey(); } } public class User { public int ID { get; set; } public string Name { get; set; } } public class SqlserverUser: UserOperate { public override void Insert(User user) { Console.WriteLine("SQL Server给User表插入一条记录"); } public override User GetUser(int id) { Console.WriteLine("SQL Server根据ID得到User表一条记录"); return null; } } public class AccessUser : UserOperate { public override void Insert(User user) { Console.WriteLine("Access给User表插入一条记录"); } public override User GetUser(int id) { Console.WriteLine("Access根据ID得到User表一条记录"); return null; } } public abstract class UserOperate { public abstract void Insert(User user); public abstract User GetUser(int id); } public enum UserOperEnum { SQLServer,Access } public class UserOperateFac { UserOperate res = null; public UserOperate GetObj(UserOperEnum op) { switch(op) { case UserOperEnum.SQLServer: res = new SqlserverUser(); break; case UserOperEnum.Access: res = new AccessUser(); break; } return res; } } }
下面是实现的工厂模式
类图如下:
源码如下:
using System; using System.Collections.Generic; using System.Linq; using System.Text; using System.Threading.Tasks; namespace ConsoleApplication1 { class Program { static void Main(string[] args) { RootFactory fac = new SqlserverUserFac(); var obj= fac.CreateOperaObj(); obj.Insert(new User() {ID=1, Name="q1" }); obj.GetUser(1); Console.ReadKey(); } } public class User { public int ID { get; set; } public string Name { get; set; } } public class SqlserverUser:UserOpera { public override void Insert(User user) { Console.WriteLine("SQL Server给User表插入一条记录"); } public override User GetUser(int id) { Console.WriteLine("SQL Server根据ID得到User表一条记录"); return null; } } public class AccessUser : UserOpera { public override void Insert(User user) { Console.WriteLine("Access给User表插入一条记录"); } public override User GetUser(int id) { Console.WriteLine("Access根据ID得到User表一条记录"); return null; } } public abstract class UserOpera { public abstract void Insert(User user); public abstract User GetUser(int id); } public abstract class RootFactory { public abstract UserOpera CreateOperaObj(); } public class SqlserverUserFac : RootFactory { public override UserOpera CreateOperaObj() { return new SqlserverUser(); } } public class AccessUserFac : RootFactory { public override UserOpera CreateOperaObj() { return new AccessUser(); } } }
现在需要变化了。
原来只有一个表User需要操作,现在我们还需要操作“部门”表。
这样出现了“多种产品系列”的问题。
下面是抽象工厂模式的演示:
类图:
源码:
using System; using System.Collections.Generic; using System.Linq; using System.Text; using System.Threading.Tasks; namespace ConsoleApplication3 { //抽象工厂 class Program { static void Main(string[] args) { IFactory fac = new SqlserverFactory(); var op= fac.CreateUser(); op.Insert(new User() { ID=1, Name="张三"}); op.GetUser(1); Console.ReadKey(); } } public class User { public int ID { get; set; } public string Name { get; set; } } public class 部门 { public int ID { get; set; } public string Name { get; set; } } public class SqlserverUser:UserOpera { public override void Insert(User user) { Console.WriteLine("SQL Server给User表插入一条记录"); } public override User GetUser(int id) { Console.WriteLine("SQL Server根据ID得到User表一条记录"); return null; } } public class AccessUser : UserOpera { public override void Insert(User user) { Console.WriteLine("Access给User表插入一条记录"); } public override User GetUser(int id) { Console.WriteLine("Access根据ID得到User表一条记录"); return null; } } public class Sqlserver部门 : 部门Opera { public override void Insert(部门 user) { Console.WriteLine("SQL Server给User表插入一条记录"); } public override 部门 GetUser(int id) { Console.WriteLine("SQL Server根据ID得到User表一条记录"); return null; } } public class Access部门 : 部门Opera { public override void Insert(部门 user) { Console.WriteLine("Access给User表插入一条记录"); } public override 部门 GetUser(int id) { Console.WriteLine("Access根据ID得到User表一条记录"); return null; } } public abstract class UserOpera { public abstract void Insert(User user); public abstract User GetUser(int id); } public abstract class 部门Opera { public abstract void Insert(部门 user); public abstract 部门 GetUser(int id); } public interface IFactory { UserOpera CreateUser(); 部门Opera Create部门(); } public class SqlserverFactory : IFactory { public UserOpera CreateUser() { return new SqlserverUser(); } public 部门Opera Create部门() { return new Sqlserver部门(); } } public class AccessFactory : IFactory { public UserOpera CreateUser() { return new AccessUser(); } public 部门Opera Create部门() { return new Access部门(); } } }
描述抽象工厂的结构图:
下面是用简单工厂改造后的抽象工厂代码:
主要改进是中需要修改dbStr这个枚举,就可以快速切换数据库类型。
避免多次调用下面的代码。
using System; using System.Collections.Generic; using System.Linq; using System.Text; using System.Threading.Tasks; namespace ConsoleApplication18 { class Program { private const SQLEnum dbStr = SQLEnum.Access; public enum SQLEnum { Access, SQLServer } static void Main(string[] args) { //RootFactory fac = new AccessUserFactory(); //var sql = fac.Create部门(); var sql = DataAccess.Create部门(); sql.Insert(new 部门() { ID = 1, Name = "张三" }); sql.GetUser(1); Console.ReadKey(); } public class DataAccess { public static UserOpera CreateUser() { UserOpera res = null; switch (dbStr) { case SQLEnum.SQLServer: res = new SqlserverUser(); break; case SQLEnum.Access: res = new AccessUser(); break; } return res; } public static 部门Opera Create部门() { 部门Opera res = null; switch (dbStr) { case SQLEnum.SQLServer: res = new Sqlserver部门(); break; case SQLEnum.Access: res = new Access部门(); break; } return res; } } public class User { public int ID { get; set; } public string Name { get; set; } } public class 部门 { public int ID { get; set; } public string Name { get; set; } } public class SqlserverUser: UserOpera { public override void Insert(User user) { Console.WriteLine("SQL Server给User表插入一条记录"); } public override User GetUser(int id) { Console.WriteLine("SQL Server根据ID得到User表一条记录"); return null; } } public class AccessUser : UserOpera { public override void Insert(User user) { Console.WriteLine("Access给User表插入一条记录"); } public override User GetUser(int id) { Console.WriteLine("Access根据ID得到User表一条记录"); return null; } } public class Sqlserver部门 : 部门Opera { public override void Insert(部门 user) { Console.WriteLine("SQL Server给部门表插入一条记录"); } public override 部门 GetUser(int id) { Console.WriteLine("SQL Server根据ID得到部门表一条记录"); return null; } } public class Access部门 : 部门Opera { public override void Insert(部门 user) { Console.WriteLine("Access给部门表插入一条记录"); } public override 部门 GetUser(int id) { Console.WriteLine("Access根据ID得到部门表一条记录"); return null; } } public abstract class UserOpera { public abstract void Insert(User user); public abstract User GetUser(int id); } public abstract class 部门Opera { public abstract void Insert(部门 user); public abstract 部门 GetUser(int id); } public class AccessUserFactory: RootFactory { public override UserOpera CreateUser() { return new AccessUser(); } public override 部门Opera Create部门() { return new Access部门(); } } public class SqlserverUserFactory: RootFactory { public override UserOpera CreateUser() { return new SqlserverUser(); } public override 部门Opera Create部门() { return new Sqlserver部门(); } } public abstract class RootFactory { public abstract UserOpera CreateUser(); public abstract 部门Opera Create部门(); } } }
---------------------
作者:hackpig
来源:www.skcircle.com
版权声明:本文为博主原创文章,转载请附上博文链接!

