盘点android中常见的设计模式(三) -- 原型模式

简介:

开闭原则

今天来说一下设计模式的6大原则之一的开闭原则。开闭原则是由勒兰特·梅耶在1988年的著作《面向对象软件构造》中首先提出的,其中提到了开闭原则的定义:对扩展开放,对修改关闭。即在程序需要进行拓展的时候,不能去修改原有的代码,实现一个热插拔的效果。简言之,是为了使程序的扩展性好,易于维护和升级。

那么开闭原则怎么实现呢?可以通过“抽象约束、封装变化”来实现开闭原则,即通过接口或者抽象类为软件实体定义一个相对稳定的抽象层,而将相同的可变因素封装在相同的具体实现类中。

原型模式:

原型模式(Prototype Pattern)是用于创建重复的对象,同时又能保证性能。这种类型的设计模式属于创建型模式,它提供了一种创建对象的最佳方式。

原型模式的运用场景一般分为两种:

  • 防止自己的实例在传入别的模块后,发生意外的修改。进行一次拷贝,再将该实例传递给别的模块,可以有效的避免意外的篡改,始终保持该实例的原始性。
  • 为了提高效率,很多时候我们需要大量的获取一个对象相同的实例,通过原型模式“克隆”出一个内部属性一样的对象是个好的选择,因为类的初始化需要耗费很多的资源。

Android中的使用:

原型模式在android中有很多运用,如常见的Intent就实现了原型模式。

      Intent intent = new Intent(PrototypeDesignActivity.this,BuilderDesignActivity.class);
      Intent cloneIntent = (Intent) intent.clone();

那么原型模式是如何实现的呢?首先需要对该类实现Cloneable接口,接着去重写clone()方法,最后在clone()方法中实现类的拷贝。

public class Intent implements Parcelable, Cloneable {
    ......

    @Override
    public Object clone() {
        return new Intent(this);
    }

    ......

}

需要注意的是,重写的clone()方法并不是Cloneable接口中的,因为该接口是一个空接口。

/**
 * @author  unascribed
 * @see     java.lang.CloneNotSupportedException
 * @see     java.lang.Object#clone()
 * @since   JDK1.0
 */
public interface Cloneable {
}

其实通过Cloneable接口的注释我们也能知道clone()方法是来自于Object类。并告诉我们有关重写此方法的详细信息请参见Object.clone()方法。

    /**
     * @return     a clone of this instance.
     * @exception  CloneNotSupportedException  if the object's class does not
     *               support the {@code Cloneable} interface. Subclasses
     *               that override the {@code clone} method can also
     *               throw this exception to indicate that an instance cannot
     *               be cloned.
     * @see java.lang.Cloneable
     */
    protected Object clone() throws CloneNotSupportedException {
        if (!(this instanceof Cloneable)) {
            throw new CloneNotSupportedException("Class " + getClass().getName() +
                                                 " doesn't implement Cloneable");
        }

        return internalClone();
    }

内容很简单,首先判断是否实现了Cloneable接口,如果没有实现就重写此方法,最终会抛出CloneNotSupportedException异常。如果实现过这个类最终返回internalClone()方法。

    /*
     * Native helper method for cloning.
     */
    private native Object internalClone();

最终我们可以看到这是一个native方法,用于辅助clone。

 

补充:

深拷贝与浅拷贝

我们知道java中分为基本数据类型和引用数据类型,深浅拷贝就是针对引用数据类型所说的。举个栗子:假如我们用对象A的clone()方法复制了对象B。这时候我们修改A中的某个引用数据类型的属性,这个时候B也跟着改变了,那么这种拷贝方式就是浅拷贝,如果B相对于A是独立的对象,不受到A中任何属性的影响,即A,B中相同的引用所指的地址不同,那么这种就是深拷贝。

常用的实现深拷贝的方式有:递归、利用JSON转换对象、利用Serializable或者Parcelable实现序列化来实现。

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章