C#设计模式系列:适配器模式(Adapter)
1. 适配器模式简介
1.1 模式定义
适配器模式:通过一个类的接口转换成客户希望的另外一个接口,使原本由于接口不兼容而不能一起工作的那些类可以一起工作。
适配器从结构上分为:类适配器和对象适配器。其中类适配器使用继承关系来对类进行适配,对象适配器使用对象引用来进行适配。
C#实现类适配器时,Target只能是接口。实现对象适配器时,Target可以是抽象类也可以是接口。
1.2 使用频率
中高
2. 类适配器模式结构
2.1 结构图
2.1.1 类适配器结构图
2.1.2 对象适配器结构图
2.2 参与者
适配器模式参与者:
◊ Target:Client所使用的目标接口,可以是接口或抽象类。由于C#不支持多类继承,故把Target定义为接口。
◊ Adaptee:需要适配的类接口。
◊ Adapter:适配器,负责Adaptee的接口与Target接口进行适配。
◊ Client:与符合Target接口的对象协调的类。
在适配器模式中,类Adapter实现适配器的功能,它在Client与Adaptee之间加入Adapter,这样Client把请求发给接口为Target的类Adapter,再由Adapter调用Adaptee,从而实现Client调用Adaptee。
3. 适配器模式结构实现
3.1 类适配器结构实现
ITarget.cs:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text; namespace DesignPatterns.AdapterPattern.Structural.ClassAdapter
{
public interface ITarget
{
void Request();
}
}
Adaptee.cs:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text; namespace DesignPatterns.AdapterPattern.Structural.ClassAdapter
{
public class Adaptee
{
public void SpecificRequest()
{
Console.WriteLine("Called SpecificRequest()");
}
}
}
Adapter.cs:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text; namespace DesignPatterns.AdapterPattern.Structural.ClassAdapter
{
public class Adapter : Adaptee, ITarget
{
public void Request()
{
this.SpecificRequest();
}
}
}
Client.cs:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text; namespace DesignPatterns.AdapterPattern.Structural.ClassAdapter
{
public class Client
{
static void Main(string[] args)
{
ITarget t = new Adapter();
t.Request();
}
}
}
运行输出:
Called SpecificRequest()
请按任意键继续. . .
3.2 对象适配器结构实现
Client需要调用Request方法,而Adaptee并没有该方法,为了使Client能够使用Adaptee类,需要提供一个类Adapter。这个类包含了一个Adaptee的实例,将Client与Adaptee衔接起来。
ITarget.cs:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text; namespace DesignPatterns.AdapterPattern.Structural.ObjectAdapter
{
public interface ITarget
{
void Request();
}
}
Target.cs:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text; namespace DesignPatterns.AdapterPattern.Structural.ObjectAdapter
{
public class Target : ITarget
{
public virtual void Request()
{
Console.WriteLine("Called Target Request()");
}
}
}
Adaptee.cs:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text; namespace DesignPatterns.AdapterPattern.Structural.ObjectAdapter
{
public class Adaptee
{
public void SpecificRequest()
{
Console.WriteLine("Called SpecificRequest()");
}
}
}
Adapter.cs:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text; namespace DesignPatterns.AdapterPattern.Structural.ObjectAdapter
{
public class Adapter : Target
{
private Adaptee _adaptee = new Adaptee(); public override void Request()
{
_adaptee.SpecificRequest();
}
}
}
Client.cs:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text; namespace DesignPatterns.AdapterPattern.Structural.ObjectAdapter
{
public class Client
{
static void Main(string[] args)
{
ITarget t = new Adapter();
t.Request();
}
}
}
4. 适配器模式实践应用
以手机充电的电源适配器为例,用适配器模式的解决方案。
4.1 类适配器结构实现
ITarget.cs
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text; namespace DesignPatterns.AdapterPattern.Practical.ClassAdapter
{
public interface ITarget
{
void GetPower();
}
}
Power.cs
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text; namespace DesignPatterns.AdapterPattern.Practical.ClassAdapter
{
public class Power
{
public void GetPower220V()
{
Console.WriteLine("从电源中得到220V的电压");
}
}
}
Adapter.cs
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text; namespace DesignPatterns.AdapterPattern.Practical.ClassAdapter
{
public class Adapter : Power, ITarget
{
public void GetPower()
{
this.GetPower220V();
Console.WriteLine("得到手机的充电电压!");
}
}
}
Client.cs
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text; namespace DesignPatterns.AdapterPattern.Practical.ClassAdapter
{
public class Client
{
static void Main(string[] args)
{
Console.WriteLine("手机:");
ITarget t = new Adapter();
t.GetPower();
}
}
}
运行输出:
手机:
从电源中得到220V的电压
得到手机的充电电压!
请按任意键继续. . .
4.2>、对象适配器结构实现
ITarget.cs
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text; namespace DesignPatterns.AdapterPattern.Practical.ObjectAdapter
{
public interface ITarget
{
void GetPower();
}
}
Power.cs
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text; namespace DesignPatterns.AdapterPattern.Practical.ObjectAdapter
{
public class Power
{
public void GetPower220V()
{
Console.WriteLine("从电源中得到220V的电压");
}
}
}
Adapter.cs
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text; namespace DesignPatterns.AdapterPattern.Practical.ObjectAdapter
{
public class Adapter : ITarget
{
public Power _power;
public Adapter(Power power)
{
this._power = power;
} /// <summary>
/// 得到想要的电压
/// </summary>
public void GetPower()
{
_power.GetPower220V();
Console.WriteLine("得到手机的充电电压!");
}
}
}
Client.cs
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text; namespace DesignPatterns.AdapterPattern.Practical.ObjectAdapter
{
public class Client
{
static void Main(string[] args)
{
Console.WriteLine("手机:");
ITarget t = new Adapter(new Power());
t.GetPower();
}
}
}
5、适配器模式应用分析
适配器模式适用情形:
◊ 当适用一个已存在的类,而它的接口不符合所要求的情况;
◊ 想要创建一个可以复用的类,该类可以与原接口的类协调工作;
◊ 在对象适配中,当要匹配数个子类的时候,对象适配器可以适配它们的父类接口。
适配器模式特点:
类适配器
◊ 使得Adapter可以重定义Adaptee的部分行为。因为Adapter是Adaptee的一个子类;
◊ 仅仅引入了一个对象,并不需要额外的指针间接得到Adaptee。
对象适配器
◊ 允许一个Adapter与多个Adaptee同时工作。Adapter也可以一次给所有的Adaptee添加功能;
◊ 使得重定义Adaptee的行为比较困难。需要生成一个Adaptee的子类,然后使Adapter引入这个子类而不是引用Adaptee本身。
C#设计模式系列:适配器模式(Adapter)的更多相关文章
- 乐在其中设计模式(C#) - 适配器模式(Adapter Pattern)
原文:乐在其中设计模式(C#) - 适配器模式(Adapter Pattern) [索引页][源码下载] 乐在其中设计模式(C#) - 适配器模式(Adapter Pattern) 作者:webabc ...
- 8.3 GOF设计模式二: 适配器模式 Adapter
GOF设计模式二: 适配器模式 Adapter 为中国市场生产的电器,到了美国,需要有一个转接器才能使用墙上的插座,这个转接 器的功能.原理?复习单实例模式 SingleTon的三个关键点 ...
- 怎样让孩子爱上设计模式 —— 7.适配器模式(Adapter Pattern)
怎样让孩子爱上设计模式 -- 7.适配器模式(Adapter Pattern) 标签: 设计模式初涉 概念相关 定义: 适配器模式把一个类的接口变换成client所期待的还有一种接口,从而 使原本因接 ...
- 二十四种设计模式:适配器模式(Adapter Pattern)
适配器模式(Adapter Pattern) 介绍将一个类的接口转换成客户希望的另外一个接口.Adapter模式使得原本由于接口不兼容而不能一起工作的那些类可以一起工作.示例有一个Message实体类 ...
- 【设计模式】适配器模式 Adapter Pattern
适配器模式在软件开发界使用及其广泛,在工业界,现实中也是屡见不鲜.比如手机充电器,笔记本充电器,广播接收器,电视接收器等等.都是适配器. 适配器主要作用是让本来不兼容的两个事物兼容和谐的一起工作.比如 ...
- Java设计模式之适配器模式(Adapter)
转载:<JAVA与模式>之适配器模式 这个总结的挺好的,为了加深印象,我自己再尝试总结一下 1.定义: 适配器模式把一个类的接口变换成客户端所期待的另一种接口,从而使原本因接口不匹配而无法 ...
- JavaScript设计模式 Item9 --适配器模式Adapter
适配器模式(转换器面模式),通常是为要使用的接口,不符本应用或本系统使用,而需引入的中间适配层类或对象的情况. 适配器模式的作用是解决两个软件实体间的接口不兼容的问题. 一.定义 适配器模式(Adap ...
- python 设计模式之适配器模式 Adapter Class/Object Pattern
#写在前面 看完了<妙味>和<华医>,又情不自禁的找小说看,点开了推荐里面随机弹出的<暗恋.橘生淮南>,翻了下里面的评论,有个读者从里面摘了一段自己很喜欢的话出来, ...
- [设计模式] 7 适配器模式 adapter
在 Adapter 模式的结构图中可以看到,类模式的 Adapter 采用继承的方式复用 Adaptee的接口,而在对象模式的 Adapter 中我们则采用组合的方式实现 Adaptee 的复用 类模 ...
- Android设计模式系列-适配器模式
对于android开发者来说起,适配器模式简直太熟悉不过,有很多应用可以说是天天在直接或者间接的用到适配器模式,比如ListView.ListView用于显示列表数据,但是作为列表数据集合有很多形式, ...
随机推荐
- LeetCode刷刷记录
一遍考研,一遍还是要刷刷题.感觉自己的时间安排的不是很好,还是要抓紧自己的日常时间,当然,也要练练刷题的手感. 1.第一题就两重循环找到索引就OK,因为是无序的,所以就不能用二分来查找,题目中每个数的 ...
- csv
csv 文件的读写:http://www.cnblogs.com/fiozhao/p/3225112.html 求取一个立方体的对角线穿个的边长为1的正方体的个数:http://www.cnblogs ...
- 关于ADO.NET连接ORACLE,使用ODAC连接中的一些问题
ADO.NET连接ORACLE时,用到ODAC组件时,有几点注意的. 1.安装的具体方法见:http://jingyan.baidu.com/article/e4511cf336ce872b845ea ...
- solr4.3 java.lang.NumberFormatException
solr java.lang.NumberFormatException 现象:定时每天全量,每隔5分钟增量DIH从mysql导入数据 solr4j返回加过Id列表,一天偶然出现 java.lang. ...
- 数据库sqlite 存储图片
SQLite可以存储 BLOB(binary large object,二进制大对象)格式数据,利用它可以在安卓应用开发中存储图片资源. 这里先讲下,怎样把数据从数据库中取出,并显示在imagView ...
- KMP匹配算法 - Number Sequence
Given two sequences of numbers : a[1], a[2], ...... , a[N], and b[1], b[2], ...... , b[M] (1 <= M ...
- Java 数列求和
编写程序,显示1+2+3+4+5+6+7+8+9的结果 public class Homework006 { public static void main(String[] args) { int ...
- PC端一些非经典兼容性问题小札
IE10默认在input框中输入内容后会显示一个‘X’按钮,方便删除输入的所有内容. 在password输入框显示一个眼睛的按钮,去掉叉叉和眼睛的方法如下: ::-ms-clear { display ...
- mysql外键添加error1215
在mysql创建表外键的过程中,由于操作不当,会提示cannot add foreign key constraint的错误. 造成此错误可能的原因如下: 1.数据类型不匹配,外键与其相关联的键必须数 ...
- 通过NFS(nfsroot)启动linux系统
Mounting the root filesystem via NFS (nfsroot) 英文原文位于inux内核源代码中的"Documentation/filesystems/nfs/ ...