【设计模式】跬步之积---工厂模式

1. 简单工厂模式

举个栗子:

public class OpertaionFactory
{
   public  static oper = null;
   switch (operate)
  {
   catch “+”:
     oper =new oper.OperationAdd()
     break;
   case “ -”:
     oper= new oper.OperationSub();
     break;
   case “*”:
     oper= new oper.OperationMul();
     break;
   case “/”:
     oper= new oper.OperationDiv();
     break;
   }
   return oper;
}

客户端代码:

 Operation oper;
 oper =operationFactory.createOperate(“+”);
 oper.NumberA=1;
 oper.NumberB=2;
 double result = oper.GetResult();

特点:
工厂类中包含了必要的逻辑判断,根据客户端的选择条件动态实例化相关的类,对于客户端来说,去除了具体产品的依赖。

举个栗子,就像你的计算机,让客户端不管该用哪个类的实例,只需要把“+”给工厂,工厂自动就给出了相应的实例,客户端只要去做运算就可以了,不同的实例会实现不同的运算。


2. 工厂方法模式

有替代的需求的时候,如何更加快速地替代。

为解决简单工厂模式,添加新功能时需要修改原来的类的不便,引进了工厂方法。

工厂方法模式:定义一个用于创建对象的接口,让子类决定实例化哪一个类。工厂方法使一个类的实例化延迟到其子类。

举个雷锋的传承人的例子:

// 社区志愿者
class Volunteer : LeiFeng
{  }

// 简单雷锋工厂
class SimpleFactory
{
   public static LeiFeng CreateLeiFeng(string type)
 {
   LeiFeng resule =null;
   switch (type)
   {
   case “ 学雷锋的大学生”:
    result = new Undergraduate();
    break;
   case “社区志愿者”:
    result= new Volunteer ();
    break;
   }
   return result;
 }
}

**客户端:**

// 简单工厂模式
LeiFeng stuedntA= SimpleFactory.CreateLeiFeng(“学雷锋的大学生”);
studentA.BuyRice();
LeiFeng studentB= SimpleFactory.CreateLeiFeng(“学雷锋的大学生”);
studentB.Sweep();
LeiFeng studentC= SimpleFactory.CreateLeiFeng(“学雷锋的大学生”)
studentC. Wash();

// 雷锋工厂
interface IFactory
{
   LeiFeng createLeiFeng();
}

//学雷锋的学生工厂
class UndergradeFactory : IFactory

{
  public LeiFeng CreateLeiFeng()
  {
  return new undergraduate();
  }
}

//社区志愿者工厂
class VolunterrFactory : IFactory
{
  public LeiFeng CreateLeiFeng()
  {
   return new Volunteer();
  }
}

客户端调用

//工厂方法模式
IFactory factory = new UndergraduateFactory();
LeiFeng student = factory.CreateLeiFeng();

student.BuyRice();
student.Sweep();
student.Wash();

3. 抽象工厂模式

解决的问题是:当程序的数据库需要进行修改的时候,如何尽可能少的减少代码的修改。

抽象工厂模式:提供一个创建一系列相关或者相互依赖对象的接口,而无需指定他们具体的类。
这里写图片描述

class DateAcess
{   
  private static readonly string db= “Sqlserver”;
  // private static readonly string db =”Access”;

  public static IUser CreateUser()
 {
  IUser  result =null;
  swtich(db)
{
   case “ Sqlserver”:
     result =new SqlserverUser();
     break;
   case “Access”:
     result =new AccessUser();
     break;
}
return result;
}
}

public static IDepartment CreatePartment()
{
   IDepartment  result= null;
   switch (db)
{
   case “Sqlserver”:
     result = new SqlserverDepartment();
     break;
   case “Access”:
     result = new AccessDepartment();
     break;
}
   return result;
}

客户端代码:
static void Main(string[] args)
{
  User user= new User();
  Department dept= new Department();
  IUser iu= Department.CreateUser();

  iu.Insert(user);
  iu.GetUser(1);

  IDepartment id = DataAccess.CreateDepartment();
  id.Insert(dept);
  id.department(1);

  Console.Read();
}

反射和抽象工厂

// 常规的写法
IUser result = new SqlseverUser();

//反射的写法
using System.Reflection;

IUser result=(IUser)Assembly.Load(“抽象工厂模式”).CreateInstance(“抽象工厂模式.SqlserverUser”);

//或者是修改配置文件,如果是数据库改变直接修改配置文件就可以了。

<? xml version=”1.0” encoding=”utf-8?>
<configuration>
   <appSettings>
      <add key=”DB” value=”Sqlserver”/>// 配置文件,可以修改成Access 
   </appSettings>
</configuration>

客户端代码:

private static readonly string db =ConfigurationManager.AppSettings[“DB”];

注意:
所有在用简单工厂的地方,都可以考虑用反射技术来去除swtich或if,解除分支判断带来的耦合。(此例中是Sqlserver 还是Access数据库的判断)


谢谢阅读~

暂时是学习笔记的连载,大家不要嫌弃哈

评论 19
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值