设计模式

设计原则

  1. 单一职责原则:一个类只负责一个功能领域中的相应职责,或者可以定义为:就一个类而言,应该只有一个引起它变化的原因。
  2. 里氏替换原则:所有引用基类(父类)的地方必须能透明地使用其子类的对象。
  3. 依赖倒置原则:抽象不应该依赖于细节,细节应当依赖于抽象。换言之,要针对接口编程,而不是针对实现编程。
  4. 接口隔离原则:使用多个专门的接口,而不使用单一的总接口,即客户端不应该依赖那些它不需要的接口。
  5. 迪米特法则:一个软件实体应当尽可能少地与其他实体发生相互作用。
  6. 开放-封闭原则:一个软件实体应当对扩展开放,对修改关闭。即软件实体应尽量在不修改原有代码的情况下进行扩展。

设计模式

单例模式

单例模式是一种常用的软件设计模式,它的核心结构中值包含一个被称为单例的特殊类。它可以保证系统中一个类只有一个实例而且该实例易于外界访问,从而控制实例个数并节约系统资源。

实现思路:
单例模式要求类能够有返回对象一个引用(永远是同一个)和一个获得该实例的方法(必须是静态方法),主要通过以下两个步骤实现:

  1. 将该类构造方法定义为私有方法,这样其他代码就无法通过调用该类的构造方法来实例化该类的对象,只有通过该类提供的静态方法来获得该类的唯一实例
  2. 在该类内部提供一个静态方法,当我们调用这个方法时,如果类持有的引用不为空就返回这个引用,如果类保持的引用为空就创建该类的实例并将实例的引用赋予该类保持的引用。

单例模式常见的写法:

  • 饿汉式(不推荐使用):
1
2
3
4
5
6
7
8
9
10
public class Singleton{
//static final单例对象,类加载的时候就初始化
private final static Singleton instance = new Singleton();
//私有构造方法,使得外界不能直接new
private Singleton(){}
//公有静态方法,对外提供获取单例接口
public static Singleton getInstance(){
return instance;
}
}

优点:线程安全。

缺点:不支持懒加载。加载这个类时就实例化了instance,浪费内存,影响性能。

  • 懒汉式(不推荐使用)
1
2
3
4
5
6
7
8
9
10
public class Singleton{
private static Singleton instance;
private Singleton(){}
public static synchronized Singleton getInstance(){
if(instance == null){
instance = new Singleton();
}
return instance;
}
}

优点:单例对象在第一次调用时才被实例化,有效节省内存,并且保证了线程安全。

缺点:同步是针对方法的,以后每次调用getInstance时(即使instance已经被实例化了),也会进行同步,造成不必要的同步开销。

  • 双重检查(推荐用)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
public class Singleton{
private static volatile Singleton instance;
private Singleton(){}
public static synchronized Singleton getInstance(){
if(instance == null){
synchronized(Singleton.class){
if(instance == null){
instance = new Singleton();
}
}
}
return instance;
}
}

优点:线程安全;延迟加载;效率较高

  • 静态内部类(推荐用)
1
2
3
4
5
6
7
8
9
public class Singleton{
private Singleton(){}
private static class SingletonInstance{
private static final Singleton instance = new Singleton()
}
public static Singleton getInstance(){
return SingletonInstance.instance
}
}

优点:避免了线程不安全,延迟加载,效率高。

  • 枚举(推荐用)
1
2
3
4
5
6
public enum EnumSingleton{
instance;
public static void whateverMethod(){

}
}

优点:系统内存中该类只存在一个对象,节省了系统资源,对于一些需要频繁创建销毁的对象,使用单例模式可以提高系统性能。

缺点:当想实例化一个单例类的时候,必须要记住使用相应的获取对象的方法,而不是使用new,可能会给其他开发人员造成困扰,特别是看不到源码的时候。