概述

抽象工厂模式(Abstract Factory)是所有形态的工厂模式中最为抽象和最具一般性的一种形态。抽象工厂模式是指当有多个抽象角色时,使用的一种工厂模式。抽象工厂模式可以向客户端提供一个接口,使客户端在不必指定产品的具体的情况下,创建多个产品族中的产品对象。


定义

抽象工厂模式(Abstract Factory),提供一个创建一系列相关或相互依赖对象的接口,而无需指定它们具体的类。


UML图解

  • AbstractFactory:声明一个创建抽象产品对象的操作接口

  • ConcreteFactory:实现创建具体产品对象的操作

  • AbstractProduct:声明一类产品对象接口

  • Product

    • 定义一个被相应具体工厂创建的产品对象

    • 实现AbstractProduct接口

  • Client:使用AbstractFactory和AbstractProduct类声明的接口

  在抽象工厂模式中,产品的创建由ConcreteFactory来完成,从结构图中可以看出,抽象工厂模式的ConcreteFactory不是负责一种具体Product的创建,而是负责一个Product族的创建。


实现

说明:

1.本次实现以博客系统为例,抽取其中的用户和文章两个对象进行说明。

2.采用三层架构,为了省事,去掉了业务逻辑层(BLL),希望理解。

示例项目结构图

示例项目类图

  • Blog.Models:模型层
  • Blog.IDAL:数据访问层接口(一类产品对象接口[AbstractProduct])
  • Blog.DAL:数据访问层分类实现(抽象产品具体分类实现)
    • MsSql:MsSql实现(抽象产品具体分类实现[ProductA1,ProductA2])
    • MySql:MySql实现(抽象产品具体分类实现[ProductB1,ProductB2])
  • Blog.Factory:抽象工厂层
    • lFactory:抽象工厂接口([AbstractFactory])
    • MsSqlFactory:MsSql具体工厂(创建具体产品对象的操作[ConcreteFactory1])
    • MySqlFactory:MySql具体工厂(创建具体产品对象的操作[ConcreteFactory2])

模型层(Blog.Models)

  • UserModel
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks; namespace AbstractFactorySamlpe.Blog.Models
{
public class UserModel
{
public int UserId { get; set; }
public string UserName { get; set; }
public string Password { get; set; }
}
}
  • PostModel
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks; namespace AbstractFactorySamlpe.Blog.Models
{
public class PostModel
{
public int PostId { get; set; }
public string PostTitle { get; set; }
public string PostContent { get; set; }
public DateTime PostTime{ get; set; }
public int PostUser { get; set; }
}
}

数据访问层接口(Blog.IDAL)

  • IUserDAL
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using AbstractFactorySamlpe.Blog.Models; namespace AbstractFactorySamlpe.Blog.IDAL
{
public interface IUserDAL
{
bool Insert(UserModel model); UserModel GetById(int id); bool Update(UserModel model); bool Delete(int id);
}
}
  • IPostDAL
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using AbstractFactorySamlpe.Blog.Models; namespace AbstractFactorySamlpe.Blog.IDAL
{
public interface IPostDAL
{
bool Insert(PostModel model); PostModel GetById(int id); bool Update(PostModel model); bool Delete(int id);
}
}

数据访问层分类具体实现(Blog.DAL)

  • Blog.DAL.MsSql

    • MsSqlPostDAL
using AbstractFactorySamlpe.Blog.IDAL;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using AbstractFactorySamlpe.Blog.Models; namespace AbstractFactorySamlpe.Blog.DAL.MsSql
{
public class MsSqlPostDAL : IPostDAL
{
public bool Delete(int id)
{
return true;
} public PostModel GetById(int id)
{
return new PostModel();
} public bool Insert(PostModel model)
{
return true;
} public bool Update(PostModel model)
{
return true;
}
}
}
  • MsSqlUserDAL
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using AbstractFactorySamlpe.Blog.IDAL;
using AbstractFactorySamlpe.Blog.Models; namespace AbstractFactorySamlpe.Blog.DAL.MsSql
{
public class MsSqlUserDAL : IUserDAL
{
public bool Delete(int id)
{
return true;
} public UserModel GetById(int id)
{
return new UserModel();
} public bool Insert(UserModel model)
{
return true;
} public bool Update(UserModel model)
{
return true;
}
}
}
  • Blog.DAL.MySql

    • MySqlPostDAL
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using AbstractFactorySamlpe.Blog.IDAL;
using AbstractFactorySamlpe.Blog.Models; namespace AbstractFactorySamlpe.Blog.DAL.MySql
{
public class MySqlPostDAL : IPostDAL
{
public bool Delete(int id)
{
return true;
} public PostModel GetById(int id)
{
return new PostModel();
} public bool Insert(PostModel model)
{
return true;
} public bool Update(PostModel model)
{
return true;
}
}
}
  • MySqlUserDAL
using AbstractFactorySamlpe.Blog.IDAL;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using AbstractFactorySamlpe.Blog.Models; namespace AbstractFactorySamlpe.Blog.DAL.MySql
{
public class MySqlUserDAL : IUserDAL
{
public bool Delete(int id)
{
return true;
} public UserModel GetById(int id)
{
return new UserModel();
} public bool Insert(UserModel model)
{
return true;
} public bool Update(UserModel model)
{
return true;
}
}
}

抽象工厂(Blog.Factory)

  • IFactory
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using AbstractFactorySamlpe.Blog.IDAL; namespace AbstractFactorySamlpe.Blog.Factory
{
public interface IFactory
{ IUserDAL CreateUser(); IPostDAL CreatePost();
}
}
  • MsSqlFactory
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using AbstractFactorySamlpe.Blog.DAL.MsSql;
using AbstractFactorySamlpe.Blog.IDAL; namespace AbstractFactorySamlpe.Blog.Factory
{
public class MsSqlFactory : IFactory
{
public IPostDAL CreatePost()
{
return new MsSqlPostDAL();
} public IUserDAL CreateUser()
{
return new MsSqlUserDAL();
}
}
}
  • MySqlFactory
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using AbstractFactorySamlpe.Blog.DAL.MySql;
using AbstractFactorySamlpe.Blog.IDAL; namespace AbstractFactorySamlpe.Blog.Factory
{
public class MySqlFactory : IFactory
{
public IPostDAL CreatePost()
{
return new MySqlPostDAL();
} public IUserDAL CreateUser()
{
return new MySqlUserDAL();
}
}
}

调用(Client)

Program

using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using AbstractFactorySamlpe.Blog.Factory;
using AbstractFactorySamlpe.Blog.IDAL; namespace AbstractFactorySamlpe
{
class Program
{
static void Main(string[] args)
{
//MSSQL
//IFactory factory = new MsSqlFactory();
//IUserDAL UserDAL = factory.CreateUser();
//IPostDAL PostDAL = factory.CreatePost(); //MySQL
IFactory factory = new MySqlFactory();
IUserDAL UserDAL = factory.CreateUser();
IPostDAL PostDAL = factory.CreatePost();
}
}
}

优点:

1、封装性,每个产品的实现类不是高层模块要关心的。

2、产品族内的约束为非公开状态。

缺点:

产品族扩展非常困难。

使用场景:

一个对象族或是一组没有任何关系的对象都有相同的约束,则可以使用抽象工厂模式。

注意事项:

产品族扩展困难,产品等级非常容易扩展,也就是横向扩展容易,纵向扩展困难。

.NET设计模式(2):1.2 抽象工厂模式(Abstract Factory)的更多相关文章

  1. 设计模式之十一:抽象工厂模式(Abstract Factory)

    抽象工厂模式: 提供了一个创建一系列相关的或相互依赖的对象的接口而不须要详细指定它们的类型. Provide an interface for creating families of related ...

  2. 乐在其中设计模式(C#) - 抽象工厂模式(Abstract Factory Pattern)

    原文:乐在其中设计模式(C#) - 抽象工厂模式(Abstract Factory Pattern) [索引页][源码下载] 乐在其中设计模式(C#) - 抽象工厂模式(Abstract Factor ...

  3. 【设计模式】抽象工厂模式 Abstract Factory Pattern

    简单工厂模式是一个工厂类根据工厂方法的参数创建不出不同的产品, 工厂方法模式是每一个产品都有一个一一对应的工厂负责创建该产品.那么今天要讲的抽象工厂模式是一个工厂能够产生关联的一系列产品.抽象工厂模式 ...

  4. 设计模式 - 抽象工厂模式(abstract factory pattern) 具体解释

    抽象工厂模式(abstract factory pattern) 详细解释 本文地址: http://blog.csdn.net/caroline_wendy/article/details/2709 ...

  5. 二十四种设计模式:抽象工厂模式(Abstract Factory Pattern)

    抽象工厂模式(Abstract Factory Pattern) 介绍提供一个创建一系列相关或相互依赖对象的接口,而无需指定它们具体的类. 示例有Message和MessageModel,Messag ...

  6. 【UE4 设计模式】抽象工厂模式 Abstract Factory Pattern

    概述 描述 提供一个创建一系列相关或相互依赖对象的接口,而无须指定它们具体的类:具体的工厂负责实现具体的产品实例 抽象工厂中每个工厂可以创建多种产品(如苹果公司生产iPhone.iPad): 工厂方法 ...

  7. 抽象工厂模式(Abstract Factory)C#实例

    抽象工厂模式(Abstract Factory)C#实例 本文出处http://www.dofactory.com/net/abstract-factory-design-pattern 一.场景描述 ...

  8. 设计模式08---设计模式之抽象工厂模式(Abstract Factory)

    1.场景模拟 举个生活中常见的例子:组装电脑,我们在组装电脑的时候,通常要选择一系列的配件,比如选择CPU时候,需要注意品牌,型号,针脚数目,主频,只有这些都确定下来,才能确定一个CPU.同样,主板也 ...

  9. 设计模式的征途—3.抽象工厂(Abstract Factory)模式

    上一篇的工厂方法模式引入了工厂等级结构,解决了在原来简单工厂模式中工厂类职责太重的原则,但是由于工厂方法模式的每个工厂只生产一类产品,可能会导致系统中存在大量的工厂类,从而增加系统开销.那么,我们应该 ...

随机推荐

  1. Hadoop学习笔记—7.计数器与自定义计数器

    一.Hadoop中的计数器 计数器:计数器是用来记录job的执行进度和状态的.它的作用可以理解为日志.我们通常可以在程序的某个位置插入计数器,用来记录数据或者进度的变化情况,它比日志更便利进行分析. ...

  2. Linux 定时任务

    200 ? "200px" : this.width)!important;} --> 介绍 本篇主要介绍Linux定时任务命令crontab的用法,crontab是定时任务 ...

  3. 跟vczh看实例学编译原理——二:实现Tinymoe的词法分析

    文章中引用的代码均来自https://github.com/vczh/tinymoe.   实现Tinymoe的第一步自然是一个词法分析器.词法分析其所作的事情很简单,就是把一份代码分割成若干个tok ...

  4. [视频],花一分钟来看看Worktile是如何为团队协作而生的

    团队协作,我们想的更深.更远.更多,花一分钟来看看我们特别奉献的故事,然后去注册一个账号,邀请小伙伴一起来工作,你会体会Worktile才是真正懂你的协作方式. 我们想做的百年公司还有很多的路,这一站 ...

  5. Android笔记——Android中visibility属性VISIBLE、INVISIBLE、GONE的区别

    在Android开发中,大部分控件都有visibility这个属性,其属性有3个分别为"visible "."invisible"."gone&quo ...

  6. IL指令汇总

    名称 说明   名称 说明 Add 将两个值相加并将结果推送到计算堆栈上.   Ldelem.I1 将位于指定数组索引处的 int8 类型的元素作为 int32 加载到计算堆栈的顶部. Add.Ovf ...

  7. C#设计模式系列:装饰模式(Decorator)

    1. 装饰模式简介 装饰模式动态地给一个对象添加额外的职责.例如一幅画有没有画框都可以挂在墙上,画就是被装饰者.但是通常都是有画框的.在挂在墙上之前,画可以被蒙上玻璃,装到框子里,所以在画上加一层画框 ...

  8. 数据结构与算法JavaScript (二) 队列

    队列是只允许在一端进行插入操作,另一个进行删除操作的线性表,队列是一种先进先出(First-In-First-Out,FIFO)的数据结构 队列在程序程序设计中用的非常的频繁,因为javascript ...

  9. [汇编与C语言关系]5. volatile限定符

    现在研究一下编译器优化会对生成的指令产生什么影响,在此基础上介绍C语言的volatile限定符.首先看下面的C程序: /* artificial device registers */ unsigne ...

  10. Python标准模块--functools

    1 模块简介 functools,用于高阶函数:指那些作用于函数或者返回其它函数的函数,通常只要是可以被当做函数调用的对象就是这个模块的目标. 在Python 2.7 中具备如下方法, cmp_to_ ...