Java设计模式之一

这几天公司没有什么事做,就看了看java的设计模式,收益匪浅!通读了一下23种设计模式,着重看了一下经常用到的几种设计模式:单例模式,工厂模式,迭代模式,代理模式,策略模式等,也敲了敲相关的代码,我觉得设计模式是一些设计思想,一些简单的问题复杂化,但是复杂的又好有道理,主要解决程序的(extensibility)可扩展性。java源码和经常用到的的一些框架如struts2和spring都使用或者封装了这些设计模式,所以我觉得设计模式太重要了,学好了它对读源码深入理解框架背后的原理,以及以后coding或者重构都会有很大帮助,所以打算花一段时间系统的学习一下,先把这本书读一遍《Head First设计模式》。

1、单例模式(Singleton Pattern)

     单例模式能够保证在JVM中只有一个实例存在。可以省去new,减少内存使用频率,还有一些核心的类在内存中只能有一个实例。

如下

package com.remote3c.singleton;public class Car {//构造方法设置为private,只能它自身创建对象,其他地方不能 new Car()private Car(){}//生产一个静态的car对象,保证JVM中只有一个private static Car car = new Car();//添加获取实例的方法public static Car getInstance(){return car;}
}

测试
package com.remote3c.singleton;public class Test {/*** @author zhangyoushuai* @version 1.0.0 * @param args*/public static void main(String[] args) {Car car1 = Car.getInstance();Car car2 = Car.getInstance();if(car1==car2){System.out.println("car1=car2");}}}

还有一种更好的写法,需要的时候再产生。

public class Singleton {  private Singleton(){}  public static Singleton getInstance(){  return SingletonInstance.instance;  }  private static class SingletonInstance{  static Singleton instance = new Singleton();  }  
} 



2、工厂模式(FactoryPattern)

当需要大量的创建对象时,可以考虑工厂模式,工厂模式特点创建对象和使用对象分开。

简单工厂,模拟 老张开车去东北,老张可以开着车,可以开着飞机,也可以骑着扫帚等等交通工具, 实现任意变换交通工具和生产交通工具的过程。

一提到任意变换,肯定用到多态,用到多态肯定就少不了继承,重写,父类引用指向子类对象。这里的继承泛指实现。

首先我们写一个交通工具的接口Moveable:

package com.remote3c.simplefactory;public interface Moveable {public void run();
}
接着写实现了这个接口的具体的交通工具car和palane

package com.remote3c.simplefactory;public class Car implements Moveable {public void run() {System.out.println("开着车,冒着烟,突突突突……去了东北");}}

package com.remote3c.simplefactory;public class Plane implements Moveable {public void run() {System.out.println("开着飞机,呜呜呜呜……的去了东北");}}

按照题意还要实现任意变换生产交通工具的生产过程,那就先建立一个交通工具的接口

package com.remote3c.simplefactory;public interface VehicleFactory {//生产交通工具  Vehicle-交通工具public Moveable produce();
}

接着写实现了这个接口的car工厂和plane工厂

package com.remote3c.simplefactory;
/*** @author zhangyoushuai* 汽车工厂*/
public class CarFactory implements VehicleFactory{public Moveable produce() {return new Car();}}

package com.remote3c.simplefactory;
/*** @author zhangyoushuai* 飞机工厂*/
public class PlaneFactory implements VehicleFactory {public Moveable produce() {return new Plane();}}
最后写测试类

package com.remote3c.simplefactory;public class Test {/*** @author zhangyoushuai* @version 1.0.0 * @param args* 模拟 老张开车去东北* 老张可以开着车,也可以开着飞机,骑着扫帚等等交通工具* 实现任意变换交通工具和生产交通工具的过程* 当需要大量的创建对象时,可以考虑工厂模式,工厂模式特点创建对象和使用对象分开*/public static void main(String[] args) {/**这里可以任意变换生产交通工具的工厂,下面去东北所乘的交通工具也随之改变当有新的交通工具添加进来的时候,只需实现moveable接口创建交通工具,再实现VehicleFactory接口创建工厂即可,*/VehicleFactory vehicle =new PlaneFactory();
//		VehicleFactory vehicle =new CarFactory();Moveable moveable =vehicle.produce();moveable.run();}}

3、抽象工厂模式(AbstractFactoryPattern)

 上面的工厂模式,有时候会造成很多工厂,工厂泛滥的情况,还有就是乘交通工具的同时再有吃着东西,打着枪等行为时该怎么办呢?

抽象工厂就是同时解决一系列产品或行为的一种模式,提供一个接口,用于创建相关或者依赖对象的家族。而不像上面那样一个工厂只生产一种产品或者行为,

而是生产一系列的产品或者行为。

下面用代码详细的模拟乘着交通工具,吃着食物,拿着武器一系列行为去东北的情况

首先创建一个抽象的总工厂

package com.remote3c.abstractfactory;public abstract class AbstractFactory {public abstract Vehicle createVehicle();//生产交通工具public abstract Weapon createWeapon();//生产武器public abstract Food createFood();//生产食物
}

接着再创建 Vehicle(交通工具),Weapon(武器),Food(食物)的抽象类

package com.remote3c.abstractfactory;public abstract class Vehicle {public abstract void run();
}
package com.remote3c.abstractfactory;public abstract class Weapon {public abstract void shoot();
}
package com.remote3c.abstractfactory;public abstract class Food {public abstract void getName();
}
同时Vehicle有run(),Weapon有shoot(),Food有getName()方法,

接着通过实现Vehicle,Weapon,Food创建真正的交通工具,武器,食物

交通工具

package com.remote3c.abstractfactory;public class Car extends Vehicle {@Overridepublic void run() {System.out.println("开着车 突突突突………………");}}
package com.remote3c.abstractfactory;public class Broom extends Vehicle {//扫帚@Overridepublic void run() {System.out.println("骑着扫帚呼啦哗啦,狼烟滚滚而去…………");}}

具体的武器
package com.remote3c.abstractfactory;public class AK47 extends Weapon {@Overridepublic void shoot() {System.out.println("拿着武器AK47,发射 突突突突突……");}}
package com.remote3c.abstractfactory;public class Magicstick extends Weapon {//魔法棒@Overridepublic void shoot() {System.out.println("挥舞着魔法棒 天灵灵,地灵灵,魔法棒快显灵……");}}

具体的食物
package com.remote3c.abstractfactory;public class Apple extends Food {@Overridepublic void getName() {System.out.println("吃着 Apple");}}
package com.remote3c.abstractfactory;public class Mushroom extends Food {//蘑菇@Overridepublic void getName() {System.out.println(" 吃着  Mushroom");}}

好了接下来该建立真正的工厂了

正常的普通的工厂

package com.remote3c.abstractfactory;public class NormalFactory extends AbstractFactory {//正常的,一般的工厂@Overridepublic Food createFood() {// TODO Auto-generated method stubreturn new Apple();}@Overridepublic Vehicle createVehicle() {// TODO Auto-generated method stubreturn new Car();}@Overridepublic Weapon createWeapon() {// TODO Auto-generated method stubreturn new AK47();}}
带有魔法的工厂
package com.remote3c.abstractfactory;public class MagicFactory extends AbstractFactory{//有魔法的工厂@Overridepublic Food createFood() {// TODO Auto-generated method stubreturn new Mushroom();}@Overridepublic Vehicle createVehicle() {// TODO Auto-generated method stubreturn new Broom();}@Overridepublic Weapon createWeapon() {// TODO Auto-generated method stubreturn new Magicstick();}}

最后终于写完了,该写测试程序啦

package com.remote3c.abstractfactory;public class Test {/*** @author zhangyoushuai* @version 1.0.0 * @param args*/public static void main(String[] args) {//在这里可以随意的切换工厂,添加工厂也不用修改现有的code,具有很强的extensibility可扩展性
//		AbstractFactory ab = new NormalFactory();AbstractFactory ab = new MagicFactory();Vehicle vehicle = ab.createVehicle();vehicle.run();Food food = ab.createFood();food.getName();Weapon weapon = ab.createWeapon();weapon.shoot();}}
测试结果

骑着扫帚呼啦哗啦,狼烟滚滚而去…………吃着  Mushroom
挥舞着魔法棒 天灵灵,地灵灵,魔法棒快显灵……

这就是抽象工厂,可以同时切换一族行为或产品,当你需要创建产品家族或想让制造的相关产品集合起来时,可以考虑使用抽象工厂。

但是抽象工厂也有它的短处,就是新增一种行为时,比如乘着交通工具,吃着东西,拿着武器的同时,再增加一种听着音乐的行为时,就需要改变抽象总工厂,会很麻烦。

如果行为不确定,最好不要用这种方法。

网上一些模式相关的链接
http://www.cnblogs.com/maowang1991/archive/2013/04/15/3023236.html

http://www.uml.org.cn/j2ee/201010214.asp

https://www.zhihu.com/question/39972591



本文来自互联网用户投稿,文章观点仅代表作者本人,不代表本站立场,不承担相关法律责任。如若转载,请注明出处。 如若内容造成侵权/违法违规/事实不符,请点击【内容举报】进行投诉反馈!

相关文章

立即
投稿

微信公众账号

微信扫一扫加关注

返回
顶部