好得很程序员自学网

<tfoot draggable='sEl'></tfoot>

详解C#的设计模式编程之抽象工厂模式的应用

这里首先以一个生活中抽象工厂的例子来实现一个抽象工厂,然后再给出抽象工厂的定义和UML图来帮助大家更好地掌握抽象工厂模式,同时大家在理解的时候,可以对照抽象工厂生活中例子的实现和它的定义来加深抽象工厂的UML图理解。抽象工厂模式比其它工厂模式更加抽象,抽象工厂模式适用与多个抽象类的情况下,通过工厂返回多个抽象类中你需要得到的具体子类实例。

抽象工厂模式比其它工厂模式更加抽象,抽象工厂模式适用与多个抽象类的情况下,通过工厂返回多个抽象类中你需要得到的具体子类实例。

举例阐述抽象工厂模式:
假如中国对邪恶国家开战。

中国装备:炸弹类,坦克类,来消灭邪恶国家。

炸弹类:导弹,核弹;

坦克类:越野车,主站坦克;

战略:

前期中国兵工厂生产:导弹,越野车,打击邪恶国家。

后期中国兵工厂生产:核弹,主站坦克,毁灭邪恶国家。

类图:

装备类代码:

?

#region 炸弹系列

abstract class Bomb

{

   abstract public void baozha();

}

/// <summary>

/// 导弹

/// </summary>

class daodanBomb :Bomb

{

   public override void baozha()

   {

     Console.WriteLine( "我是一颗中国造导弹,来轰炸不老实的小邪恶国家!" );

   }

}

/// <summary>

/// 核弹

/// </summary>

class hedanBomb : Bomb

{

   public override void baozha()

   {

     Console.WriteLine( "我是一颗中国造核弹,来轰炸不老实的小邪恶国家!" );

   }

}

#endregion

 

#region 坦克系列

abstract class Tank

{

   abstract public void go();

}

/// <summary>

/// 越野车

/// </summary>

class yueyeTank : Tank

{

   public override void go()

   {

     Console.WriteLine( "我是一颗中国造越野车,来踏平不老实的小邪恶国家!" );

   }

}

/// <summary>

/// 主站坦克

/// </summary>

class zhuzhanTank : Tank

{

   public override void go()

   {

     Console.WriteLine( "我是一颗中国造主站坦克,来踏平不老实的小邪恶国家!" );

   }

}

#endregion工厂类代码

 

 

#region 中国兵工厂

abstract class chinaFactory

{

   //装甲车制造车间

   public abstract Tank CreateTank();

   //炸弹知道车间

   public abstract Bomb CreateBomb();

}

//兵工厂前期制造

class qianqiFactory : chinaFactory

{  

   public override Bomb CreateBomb()

   {

     //导弹

     return new daodanBomb();

   }

   public override Tank CreateTank()

   {

     //越野车

     return new yueyeTank();

   }

}

//兵工厂后期制造

class houqiFactory : chinaFactory

{

   public override Bomb CreateBomb()

   {

     //核弹

     return new hedanBomb();

   }

   public override Tank CreateTank()

   {

     //主站坦克

     return new zhuzhanTank();

   }

}

#endregion客户端代码:(打仗)

 

 

// 备战

class Make

{

   //装备

   private Bomb bomb;

   private Tank tank;

   //制造加工

   public Make(chinaFactory factory)

   {

     bomb = factory.CreateBomb();

     tank = factory.CreateTank();

   }

 

   //开始打仗

   public void warStar()

   {

     //炸弹类爆炸

     bomb.baozha();

     //战车类前进

     tank.go();

   }

 

}

public class start

{

   public static void Main()

   {

     //大战前期

     chinaFactory qianqiMake = new qianqiFactory();

     Make qianqi = new Make(qianqiMake);

     qianqi.warStar();

 

     //点任意键,进行后期攻势!!

     Console.ReadKey();

 

     //大战后期

     chinaFactory houqiMake = new houqiFactory();

     Make houqi = new Make(houqiMake);

     houqi.warStar();

 

     Console.WriteLine( "钓鱼岛是中国的,神圣不可侵犯!小邪恶国家,滚开!!" );

     Console.ReadLine();

   }

}

 

抽象工厂模式的定义和类图

抽象工厂允许客户使用抽象的接口来创建一组相关产品,而不需要知道或关心实际生产出的具体产品是什么。这样客户就可以从具体产品中被解耦。下面通过抽象工模式的类图来了解各个类中之间的关系:

抽象工厂的分析
抽象工厂模式将具体产品的创建延迟到具体工厂的子类中,这样将对象的创建封装起来,可以减少客户端与具体产品类之间的依赖,从而使系统耦合度低,这样更有利于后期的维护和扩展,这真是抽象工厂模式的优点所在,然后抽象模式同时也存在不足的地方。下面就具体看下抽象工厂的缺点(缺点其实在前面的介绍中以已经涉及了):

抽象工厂模式很难支持新种类产品的变化。这是因为抽象工厂接口中已经确定了可以被创建的产品集合,如果需要添加新产品,此时就必须去修改抽象工厂的接口,这样就涉及到抽象工厂类的以及所有子类的改变,这样也就违背了[开发——封闭]原则。

知道了抽象工厂的优缺点之后,也就能很好地把握什么情况下考虑使用抽象工厂模式了,下面就具体看看使用抽象工厂模式的系统应该符合那几个前提:

一个系统不要求依赖产品类实例如何被创建、组合和表达的表达,这点也是所有工厂模式应用的前提。
这个系统有多个系列产品,而系统中只消费其中某一系列产品
系统要求提供一个产品类的库,所有产品以同样的接口出现,客户端不需要依赖具体实现。


.NET中抽象工厂模式实现
抽象工厂模式在实际中的应用也是相当频繁的,然而在我们.NET类库中也存在应用抽象工厂模式的类,这个类就是System.Data.Common.DbProviderFactory,这个类位于System.Data.dll程序集中,该类扮演抽象工厂模式中抽象工厂的角色,我们可以用reflector反编译工具查看该类的实现:

?

/// 扮演抽象工厂的角色

/// 创建连接数据库时所需要的对象集合,

/// 这个对象集合包括有 DbConnection对象(这个是抽象产品类,如绝味例子中的YaBo类)、DbCommand类、DbDataAdapter类,针对不同的具体工厂都需要实现该抽象类中方法,

public abstract class DbProviderFactory

{

   // 提供了创建具体产品的接口方法

   protected DbProviderFactory();

   public virtual DbCommand CreateCommand();

   public virtual DbCommandBuilder CreateCommandBuilder();

   public virtual DbConnection CreateConnection();

   public virtual DbConnectionStringBuilder CreateConnectionStringBuilder();

   public virtual DbDataAdapter CreateDataAdapter();

   public virtual DbDataSourceEnumerator CreateDataSourceEnumerator();

   public virtual DbParameter CreateParameter();

   public virtual CodeAccessPermission CreatePermission(PermissionState state);

}

DbProviderFactory类是一个抽象工厂类,该类提供了创建数据库连接时所需要的对象集合的接口,实际创建的工作在其子类工厂中进行,微软使用的是SQL Server数据库,因此提供了连接SQL Server数据的具体工厂实现,具体代码可以用反编译工具查看,具体代码如下:

 

/// 扮演着具体工厂的角色,用来创建连接SQL Server数据所需要的对象

public sealed class SqlClientFactory : DbProviderFactory, IServiceProvider

{

   // Fields

   public static readonly SqlClientFactory Instance = new SqlClientFactory();

   // 构造函数

   private SqlClientFactory()

   {

   }

      

   // 重写抽象工厂中的方法

   public override DbCommand CreateCommand()

   { // 创建具体产品

     return new SqlCommand();

   }

   public override DbCommandBuilder CreateCommandBuilder()

   {

     return new SqlCommandBuilder();

   }

   public override DbConnection CreateConnection()

   {

     return new SqlConnection();

   }

   public override DbConnectionStringBuilder CreateConnectionStringBuilder()

   {

     return new SqlConnectionStringBuilder();

   }

   public override DbDataAdapter CreateDataAdapter()

   {

     return new SqlDataAdapter();

   }

   public override DbDataSourceEnumerator CreateDataSourceEnumerator()

   {

     return SqlDataSourceEnumerator.Instance;

   }

   public override DbParameter CreateParameter()

   {

     return new SqlParameter();

   }

   public override CodeAccessPermission CreatePermission(PermissionState state)

   {

     return new SqlClientPermission(state);

   }

}

因为微软只给出了连接SQL Server的具体工厂的实现,我们也可以自定义连接Oracle、MySql的具体工厂的实现。

dy("nrwz");

查看更多关于详解C#的设计模式编程之抽象工厂模式的应用的详细内容...

  阅读:65次