Android中的设计模式-适配器模式

适配器模式

从名字上就可以看出适配器是为了针对接口不匹配的情况,而做出的兼容方法,

假设我们有一个已经存在的类Adaptee,其中有一些已经存在并实现好的方法methodA。但是客户不希望调用这个类,而是希望调用一个特定的接口例如Target接口。

于是如果想要调用Adaptee.methodA()方法,创建一个Adapter类实现客户要求的Target接口,Target接口中假设客户希望调用callMethodA()方法来实现Adaptee.methodA()方法功能。能够想到的就是以下两种方式:

类的适配器模式

让Adapter类实现Target接口接口同时继承Adaptee类,这样Adapter类就继承了Adaptee.methodA(),在其callMethodA()中调用父类的methodA()方法即可。客户新建Adapter类对象,就可以通过Target接口调用Adapter.methodA()。

类图

代码实现

等待被适配的Adaptee

public class Adaptee {
    public void methodA(){
        System.out.println("I am the methodA in Adaptee");
    }
}

客户期待的Target接口

public interface Target {
    public void callMethodA();
    public void otherMethod();
}

继承了Adaptee并实现Target接口的适配者

public class Adapter extends Adaptee implements Target {
    @Override
    public void callMethodA() {
        super.methodA();
    }
    @Override
    public void otherMethod() {
        System.out.println("I am the otherMethod in Adapter");
    }
}

客户类测试

public class Client {

    public static void main(String[] args) {
        Adapter mAdapter = new Adapter();
        mAdapter.callMethodA();
        mAdapter.otherMethod();
    }

}

输出结果

I am the methodA in Adaptee
I am the otherMethod in Adapter

对象的适配器模式

让Adapter类中持有一个Adaptee类的实例,在Adapter类实现Target接口的methodA()方法时,在其中调用Adaptee实例的methodA()方法即可。

类图

代码实现

在上面的类的适配器基础上,只需要修改Adapter和客户类即可。

继承了Adaptee并实现Target接口的适配者


public class Adapter implements Target {
    private Adaptee mAdaptee;

    public Adapter(Adaptee mAdaptee) {
        this.mAdaptee = mAdaptee;
    }
    @Override
    public void callMethodA() {
        this.mAdaptee.methodA();
    }
    @Override
    public void otherMethod() {
        System.out.println("I am the otherMethod in Adapter");
    }
}

客户类测试

public class Client {

    public static void main(String[] args) {
        Adaptee mAdaptee=new Adaptee();
        Adapter mAdapter = new Adapter(mAdaptee);
        mAdapter.callMethodA();
        mAdapter.otherMethod();
    }

}

输出结果也是一样的

输出结果

I am the methodA in Adaptee
I am the otherMethod in Adapter

两种适配器的对比

两种模式各有利弊,类的适配器模式已经继承了Adaptee类,就没法再继承其他的类,这时它的弊端,不过好处就是逻辑比较清晰,适合只适配单一的Adaptee的情况。对象的适配器模式则没有继承的限制,采用聚合的方式来适配待适配的类。个人个倾向于对象的适配器模式这种适配器方式,耦合性更低。

缺省适配器模式

适配器还有第三种模式,看起来和上面的两种适配器模式不太一样,

对于一个定义了较多方法的接口,我们实现该接口的时候,一来实现这么多的方法很麻烦。二来有些方法我们并不需要,都实现了反而混淆了重点。

为了解决这个问题,就是用一个抽象类继承该接口,并在抽象类中使用空实现来实现接口中的方法。(也不一定,有些情况抽象类中会有接口中的方法的默认实现,而继承它的子类中只需要完成其特有的一些方法,或者在原有方法的基础上进行增加。例如Android中的PhoneBase类,BaseAdapter类等)。

类图

代码实现

public interface Target {
    public void A();
    public void B();
    public void C();
    public void D();
    public void E();
    public void F();
}

public abstract class AbstractTarget implements Target {

    @Override
    public void A() {
    }
    //可以留一个B方法不实现,B还是抽象的,留给子类必须实现
    @Override
    public void C() {
        System.out.println("I am C in AbstractTarget");
    }

    @Override
    public void D() {
    }

    @Override
    public void E() {
    }

    @Override
    public void F() {

    }

}

public class ConcreteTarget extends AbstractTarget {

    @Override
    public void B() {//B是必须实现的
        System.out.println("I am B in ConcreteTarget");
    }

    @Override
    public void A() {//选择性的重写A和C方法
        System.out.println("I am A in ConcreteTarget");
    }

    @Override
    public void C() {
        super.C();
        System.out.println("I am C in ConcreteTarget");
    }

}

测试

    public static void main(String[] args) {
        Target mTarget = new ConcreteTarget();
        mTarget.A();
        mTarget.B();
        mTarget.C();
    }

Android中的适配器模式

Android中最常见的适配器模式就属于Android中的Adapter了,其应用融合了缺省适配器模式和对象的适配器模式

抽象类BaseAdapter实现ListAdapter和SpinnerAdapter两个接口,而这两个接口都是继承自Adapter接口,这两个接口分别又定义了自己的方法

public abstract class BaseAdapter implements ListAdapter, SpinnerAdapter 

不过BaseAdapter中并未实现接口中的全部方法

SimpleAdapter则继承了BaseAdapter,并实现了所有没实现的接口方法,有些BaseAdapter已经实现的方法,并没有实现。

public class SimpleAdapter extends BaseAdapter

这里就是上面的缺省适配器模式。

那么对象的适配器呢,

当我们使用SimpleAdapter时,例如:

ListView.setAdapter(new SimpleAdapter(this, getData(path),
                android.R.layout.simple_list_item_1, new String[] { "title" },
                new int[] { android.R.id.text1 }));

先看一下SimpleAdapter构造函数

    public SimpleAdapter(Context context, List<? extends Map<String, ?>> data,
            int resource, String[] from, int[] to)

其中第2个参数是一个Map的队列,对应每一个List的Item的数据,第3个参数则是展开这个Item的View的layout资源的整形ID。第4个参数from数组是第2个参数的Map的key,最后一个参数to数组则是from参数的每一个key对应的数据放置在哪个组件里。

在ListView调用onMeasure确定组件尺寸时,就会调用到mAdapter.getCount(),调用这个SimpleAdapter的getCount()函数:

    public int getCount() {
        return mData.size();
    }
    public Object getItem(int position) {
        return mData.get(position);
    }

间接调用之前创建SimpleAdapter时构造函数传递的data数据。

在绘制的时候,则会调用

mAdapter.getView(position, null, this)

获取适配器所适配的数据所对应的View来进行绘制。

所以这里SimpleAdapter就是对data对象的对象适配器模式,如果不使用适配器,ListView直接持有data数据当然也可以得到数据。但是ListView使用Adapter的精髓就是不需要去管数据是什么,只需要创建不同的Adapter,就可以做出不同效果,含有不同组件的ListView。

时间: 2024-08-12 07:41:35

Android中的设计模式-适配器模式的相关文章

[Android]GOF23种设计模式 &amp; Android中的设计模式

GOF23种设计模式 设计原则: 1. 单一职责原则(SRP):就一个类而言,应该仅有一个引起它变化的原因 2. 开放-封闭原则(OCP):软件实体(类.模块.函数等)应该可以扩展,但是不可修改.即对于扩展是开放的, 对于修改是封闭的. 3. 依赖倒转原则: A. 高层模块不应该依赖低层模块,两个都应该依赖抽象.B.抽象不应该依赖细节,细节应该依赖抽象.说白了,就是要针对接口编程,不要对实现编程. 4. 迪米特法则(LoD):如果两个类不必彼此直接通信,那么这两个类就不应该发生直接的相互作用.如

Android中的设计模式-单例模式

Android中的设计模式-单例模式 单例模式算是比较常用的模式,在Java中如果想要一个JVM中只存在某个类的一个实例,就需要使用到单例模式,而只存在一个实例的需求一般是因为: 1,对象实例比较大和复杂,创建开销很大. 2,只需要一个实例来维护整个功能的流程与交互. 例如Android中的电话应用启动时,对于单卡单待的电话,只创建一个Phone对象,用来管理RIL,CallTracker,ServiceStateTracker等对象,手机中不存在第二个Phone对象去和RILC通信. 类图 单

[转] Android中的设计模式-备忘录模式

转自Android中的设计模式-备忘录模式 定义 备忘录设计模式的定义就是把对象的状态记录和管理委托给外界处理,用以维持自己的封闭性. 比较官方的定义 备忘录模式(Memento Pattern)又叫做快照模式(Snapshot Pattern)或Token模式,是GoF的23种设计模式之一,属于行为模式. 定义:在不破坏封闭的前提下,捕获一个对象的内部状态,并在该对象之外保存这个状态.这样以后就可将该对象恢复到原先保存的状态. 角色 笔记本:很多的内部状态需要被建立一个备忘录来管理,创建和取出

Android中的设计模式

一.设计模式的分类 总体来说23种设计模式分为三大类: 创建型模式,共五种:工厂方法模式.抽象工厂模式.单例模式.建造者模式.原型模式. 结构型模式,共七种:适配器模式.装饰器模式.代理模式.外观模式.桥接模式.组合模式.享元模式. 行为型模式,共十一种:策略模式.模板方法模式.观察者模式.迭代子模式.责任链模式.命令模式.备忘录模式.状态模式.访问者模式.中介者模式.解释器模式. 其实还有两类:并发型模式和线程池模式. 二.Android中常见的八种设计模式 一般来说,常用的设计模式有以下八种

Android中的设计模式-工厂方法模式

简单工厂&工厂方法 一直以来总是分不清简单工厂,工厂方法,抽象工厂这三个设计模式的区别,倒不是不理解其区别,而是总是记忆混淆,傻傻分不清楚,所以再重新总结一下区别,并记录下来,下次再混淆时,可以拿出来看看.这节先说简单工厂和工厂方法,下一节再说抽象工厂. 工厂方法中其实就包含了简单工厂,简单工厂也称为静态工厂方法, 简单工厂模式(Simple Factory) 类图 简单工厂模式又称为静态工厂方法模式,是工厂方法模式的一种,简单工厂模式的实质是由一个工厂类根据传入的参数,动态决定应该创建哪一个产

Android中的设计模式-观察者模式

观察者模式 观察者模式,有时又被称为发布-订阅Subscribe>模式.模型-视图View>模式.源-收听者Listener>模式或从属者模式.一个目标物件管理所有相依于它的观察者物件,并且在它本身的状态改变时主动发出通知. 观察者模式算是一个比较常用的模式了,使用上就像是订阅RSS,当有新的新闻更新,接受订阅的主题就会向每一个订阅者发送消息,这里的发送消息一般是调用订阅者的已经定义好的函数,如OnEvent()等.也可以通过其他方式发送消息给订阅者,比如Handler.不拘泥于固定的方

Android中的设计模式之观察者模式

参考 <设计模式:可复用面向对象软件的基础 >5.7 Observer 观察者 对象行为型模式 <设计模式解析> 18.4 Observer模式 <Android源码设计模式解析与实战>第12章 解决,解耦的钥匙--观察者模式 本人能力有限,如有明显错误,不规范的地方,请指正,谢谢. 意图 定义对象间的一种一对多的依赖关系,当一个对象的状态发生改变时,所有依赖于它的对象都得到通知并自动更新. 别名 依赖(Dependents)发布-订阅(Publish-Subscrib

Android中的设计模式-抽象工厂模式

抽象工厂模式(Abstract Factory) 先上类图吧,自己懒得画了,找了个现成的 抽象工厂的引入是根据需求而产生的,说到这里先要提到一个名字-产品族(Product Family),还是以生产汽车为例,我想要一个上汽的汽车工厂能够同时生产一款MPV,一款SUV和一款Sedan,那比如说它就是上海通用别克的工厂啦,可以生产MPV GL8,生产SUV 昂科威,可以生产Sedan 君威,这几款产品就算是一个产品族.作为公司高层,肯定是希望工厂能够有能力同时生产这三款车,将这个工程抽象出来,就成

寻找android中的设计模式(一)

 概述 维护android系统中的联系人模块有一段时间了,最近开始学习java设计模式,对书(HEAD_FIRST设计模式)中精彩设计非常崇拜和对OO原则有了更深刻的理解.作为对设计模式的初学者,我将记录对它的追求之路.该系列文章将结合联系人应用,寻找google原生代码中设计模式. 寻找单例模式 定义:确保一个类只有一个实例,并提供一个全局访问点. 对于初学单例模式,我往往会这样写: public class Singleton { private static Singleton mSi