设计模式笔记

设计模式

简单工程模式

OperationFactory类(工厂类)
class operationFactory{
	public operation createOperation(String countType){
		operation oper=null;
		switch (countType) {
		case "+":
			oper=new operationAdd();
			break;
		case "-":
			oper=new operationSub();
			break;
		case "/":
			oper=new operationDiv();
			break;
		case "*":
			oper=new operationMul();
			break;

		}
		return oper;
	}
}
Operation类(产品抽象父类)
class operation{
	
	private double numberA=0;
	private double numberB=0;
	
	public double getNumberA() {
		return numberA;
	}

	public void setNumberA(double numberA) {
		this.numberA = numberA;
	}

	public double getNumberB() {
		return numberB;
	}

	public void setNumberB(double numberB) {
		this.numberB = numberB;
	}

	@Override
	public String toString() {
		return "operation [numberA=" + numberA + ", numberB=" + numberB + "]";
	}
	public double getResult(){
		double result=0;
		return result;
	}
}
OperationAdd类和OperationSub类(具体产品实现子类)
class operationAdd extends operation{
	public double getResult(){
		System.out.println("用到+了");
		System.out.println(getNumberA());
		return getNumberA()+getNumberB();
		
	}
}
class operationSub extends operation{
	public double getResult(){
		return getNumberA()-getNumberB();
		
	}
}
客户端
double numberA,numberB;
	String countType;
	operation oper;
	Scanner s=new Scanner(System.in);
	
	System.out.println("请输入运算符 +、-、*、/:");
	countType=s.next();
	oper=new operationFactory().createOperation(countType);
	System.out.println("请输入数字A:");
	numberA=s.nextDouble();
	oper.setNumberA(numberA);
	System.out.println("请输入数字B:");
	numberB=s.nextDouble();
	oper.setNumberB(numberB);
	System.out.println(oper.toString());;

	System.out.println("结果是:"+oper.getResult());

工厂模式

与简单的区别是工厂有多个具体的生产产品的工厂方法

Product类(产品类)
//抽象产品,提供产品的接口
interface Product{
	public void show();
}

//具体产品1,实现了抽象产品中的抽象方法
class ConcreteProduct1 implements Product{
	public void show() {
System.out.println("产品1");		
	}
	
}
//具体产品2,实现了抽象产品中的抽象方法
class ConcreteProduct2 implements Product{
	public void show() {
		System.out.println("产品2");		
	}
	
}

XXXFactory(工厂类)


//抽象工厂,提供厂品的接口
interface AbstractFactory{
	public Product newProduct();
}
//具体厂品1,实现了抽象厂品的抽象方法
class ConcreteFactory1 implements AbstractFactory{
	@Override
	public Product newProduct() {
		System.out.println("具体工厂1生成-->具体产品1");
		return new ConcreteProduct1();
	}
}

//具体厂品2,实现了抽象厂品的抽象方法
class ConcreteFactory2 implements AbstractFactory{
	@Override
	public Product newProduct() {
		System.out.println("具体工厂2生成-->具体产品2");
		return new ConcreteProduct2();
	}
}
客户端
public static void main(String[] args) {
		Product a;
		AbstractFactory af;
		af=(AbstractFactory) FatoryReadXml.getObject();
		a=af.newProduct();
		a.show();
	}
xml配置
class FatoryReadXml
{
    //该方法用于从XML配置文件中提取具体类类名,并返回一个实例对象
    public static Object getObject()
    {
        try
        {
            //创建文档对象
            DocumentBuilderFactory dFactory=DocumentBuilderFactory.newInstance();
            DocumentBuilder builder=dFactory.newDocumentBuilder();
            Document doc;                           
            doc=builder.parse(new File("src/config1.xml"));        
            //获取包含类名的文本节点
            NodeList nl=doc.getElementsByTagName("className");
            Node classNode=nl.item(0).getFirstChild();
            String cName="creationtype."+classNode.getNodeValue();
            System.out.println("classNode:::"+classNode.getNodeValue());
            System.out.println("cName:::"+cName);
            //System.out.println("新类名:"+cName);
            //通过类名生成实例对象并将其返回
            Class<?> c=Class.forName(cName);
              Object obj=c.newInstance();
            return obj;
         }  
         catch(Exception e)
         {
                   e.printStackTrace();
                   return null;
         }
    }
}
config1.xml
<?xml version="1.0" encoding="UTF-8"?>
<config>
	<className>ConcreteFactory1</className>
</config>

例2

EmployeeServiceImpl类(具体产品类)
public class EmployeeServiceImpl extends BaseServiceImpl<User,UserQuery> implements UserService{

	@Override
	public User login(String loginName, String password) {
		QueryRunner queryRunner = new QueryRunner(JDBCUtil.getDataSource());
		String SQL = "select * from user where loginName = ? and password = ?";
		try {
			//BeanHandler将ResultSet的第一条记录--->User对象
			//数据库的列名---User属性名对应
			return queryRunner.query(SQL,new BeanHandler<User>(User.class),new Object[] {loginName,password});
		} catch (SQLException e1) {
			e1.printStackTrace();
		}
		return null;
	}
	
	@Override
	public int add(User t) {
		//password 默认值
	    t.setPassword(SysUtil.getValue("password"));
		return super.add(t);
	}
}
ServiceFactory类(工厂类)
/*
 * Service的工厂
 */
public class ServiceFactory {
	
	//容器
	private static final Map container = new HashMap();
	
	//单例
	private ServiceFactory() {
		
	}
	
	//提前创建好-->容器(通过配置文件指定工厂需要创建的对象)
	static {
		 //加载factory.properties文件
		
		InputStream inputStream = ServiceFactory.class.getClassLoader().getResourceAsStream("factory.properties");
		 
		Properties properties = new Properties();
		try {
			properties.load(inputStream);
		} catch (IOException e) {
			e.printStackTrace();
		}finally {
			if(inputStream!=null){
				try {
					inputStream.close();
				} catch (IOException e) {
					e.printStackTrace();
				}
			}
		}
		
		Set<Object> keies = properties.keySet();
		try {
		    for(Object key : keies) {
		    	container.put(key, Class.forName(properties.get(key)+"").newInstance());
		    }
		} catch (InstantiationException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		} catch (IllegalAccessException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		} catch (ClassNotFoundException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}
	}
	
	//并且提供获取service实例的方法 
	/**
	 * 
	 * @param serviceName  实例名
	 * @return 
	 */
	public static <T> T getService(String serviceName) {
		return (T) container.get(serviceName);
	}
}
factory. properties (配置文件)
userService=com.neuedu.catering.service.impl.EmployeeServiceImpl
UserTableModel类(使用工厂的类)
public class UserTableModel extends AbstractTableModel{
	
	private String [] columnName = {"id","名字","登录名","等级","电话"};

	private UserService userService = ServiceFactory.getService("userService");
	
	private Page<User> page;
	
	public Page<User> getPage() {
		return page;
	}


	public void query(UserQuery userQuery) {
		//查找全部数据
		page = userService.query(userQuery);
	}
	
	
	@Override
	public int getRowCount() {
		return page.getDatas().size();
	}

	@Override
	public int getColumnCount() {  
		return columnName.length;
	}

	@Override
	public Object getValueAt(int rowIndex, int columnIndex) {
		User user = page.getDatas().get(rowIndex);
		if(columnIndex==0) {
			return user.getId();
		}else if(columnIndex==1) {
			return user.getName();
		}else if(columnIndex==2) {
			return user.getLoginName();
		}else if(columnIndex==3) {
			return user.getLevel();
		}else if(columnIndex==4) {
			return user.getPhone();
		}else {
			return null;
		}
	}
	 
	@Override
	public String getColumnName(int column) {
		return columnName[column];
	}
	
	
}

抽象工厂

定义

抽象工厂的代码和工厂模式的代码类型,其中的区别在于抽象工厂中的具体工厂是生产一族的产品,如一个产品等级:各种品牌的冰箱就是一个抽象冰箱+多个某品牌的具体实现的字类,工厂方法中不是对一个个冰箱一一建立工厂而是对一个品牌建立工厂。ps:抽象产品类不止一个(电视冰箱空调等)。

优点:

1.增加产品族很方便,符合开闭原则。因为所有产品都准备好了,只需加上一个品牌。

2.隔离了具体类的生成,保证客户端不知道什么被创建

缺点:当代码量变大时,增加一个产品等级后会变的很麻烦,如建了很多个品牌工厂后,又要增加一种产品如手机,那么每个品牌工厂都要加上这个产品。

原型模式

作用

1、基本就是你需要从A的实例得到一份与A内容相同,但是又互不干扰的实例的话,就需要使用原型模式。

2、当然有的时候,如果我们并不需要基于现有的对象复制新的对象,或者我们需要的就是一个干净的空对象,那么我的首先还是工厂模式或者抽象工厂模式

1、为什么不用new直接新建对象,而要用原型模式?

首先,用new新建对象不能获取当前对象运行时的状态,其次就算new了新对象,在将当前对象的值复制给新对象,效率也不如原型模式高。

2、为什么不直接使用拷贝构造函数,而要使用原型模式?

原型模式与拷贝构造函数是不同的概念,拷贝构造函数涉及的类是已知的,原型模式涉及的类可以是未知的(基类的拷贝构造函数只能复制得到基类的对象)。

浅克隆与深克隆

浅:不会复制引用类型的成员变量的值

深:所有成员变量都复制

客户端
public class prototype {
	public static void main(String[] args) throws CloneNotSupportedException {
		Realizetype r1=new Realizetype();
		Realizetype r2=(Realizetype)r1.clone();
		System.out.println(r1==r2);
	}

}

false

Realizetype类(具体原型类)
class Realizetype implements Cloneable{
	Realizetype(){
		System.out.println("具体原型类创建成功!");
	}
	public Object clone() throws CloneNotSupportedException{
		System.out.println("具体原型复制成功!");
		return (Realizetype)super.clone();
		
	}
}

策略模式

定义

定义一系列算法,将每一个算法封装起来,并让它们可以相互替换。策略模式让算法可以独立于使用它的客户变化

Strategy类( 抽象策略类 )
public abstract class Strategy {
    public abstract void algorithm();  //声明抽象算法
}

ConcreteStrategyA类 (具体策略类)
public class ConcreteStrategyA extends Strategy {
    //算法的具体实现
    public void algorithm() {
        //算法A
    }
}

Context类 (实现中间层环境类)
public class Context {
    private Strategy strategy; //维持一个对抽象策略类的引用

    //注入策略对象
    public void setStrategy(Strategy strategy) {
        this.strategy= strategy;
    }

    //调用策略类中的算法
    public void algorithm() {
        strategy.algorithm();
    }
}

客户端代码
……
Context context = new Context();
Strategy strategy;
strategy = new ConcreteStrategyA(); //可在运行时指定类型,通过配置文件和反射机制实现
context.setStrategy(strategy);
context.algorithm();
……

桥接模式

定义

桥接模式:抽象部分与它的实现部分解耦,使得两者都能够独立变化。

桥接模式的定义
又被称为柄体(Handle and Body)模式或接口(Interface)模式
用抽象关联取代了传统的多层继承
将类之间的静态继承关系转换为动态的对象组合关系

关键

在抽象类中注入实现类接口的对象,这样就实现解耦。而不是抽象和继承实现他的类解耦

不同图片格式在不同操作系统上的解析例子

Image类(抽象图像类)
//抽象图像类,充当抽象类
public abstract class Image {
	protected ImageImp imp;

    //注入实现类接口对象
	public void setImageImp(ImageImp imp) {
		this.imp = imp;
	} 

	public abstract void parseFile(String fileName);
}
GIFImage类(扩充抽象类)

//GIF格式图像类,充当扩充抽象类
public class GIFImage extends Image {
	public void parseFile(String fileName) {
      //模拟解析GIF文件并获得一个像素矩阵对象m;
      Matrix m = new Matrix(); 
      imp.doPaint(m);
      System.out.println(fileName + ",格式为GIF。");
  }
}
ImageImp类(实现类接口)
//抽象操作系统实现类,充当实现类接口
public interface ImageImp {
	public void doPaint(Matrix m);  //显示像素矩阵m
}

WindowsImp类(接口的具体实现类)
//Windows操作系统实现类,充当具体实现类
public class WindowsImp implements ImageImp {
  public void doPaint(Matrix m) {
  	//调用Windows系统的绘制函数绘制像素矩阵
  	System.out.print("在Windows操作系统中显示图像:");
  }
}
客户端
public class Client {
	public static void main(String args[]) {
		Image image;
		ImageImp imp;
		image = (Image)XMLUtil.getBean("image");
		imp = (ImageImp)XMLUtil.getBean("os");
		image.setImageImp(imp);
		image.parseFile("小龙女");
	}
}
xml
config.xml
<?xml version="1.0"?>
<config>
	<!--RefinedAbstraction-->
	<className>designpatterns.bridge.GIFImage</className> 
	<!--ConcreteImplementor-->
	<className>designpatterns.bridge.WindowsImp</className>
</config>
XMLUtil类
public class XMLUtil {
	//该方法用于从XML配置文件中提取具体类类名,并返回一个实例对象
	public static Object getBean(String args) {
		try {
			//创建文档对象
			DocumentBuilderFactory dFactory = DocumentBuilderFactory.newInstance();
			DocumentBuilder builder = dFactory.newDocumentBuilder();
			Document doc;							
			doc = builder.parse(new File("src//designpatterns//bridge//config.xml")); 
			NodeList nl=null;
			Node classNode=null;
			String cName=null;
			nl = doc.getElementsByTagName("className");
			
			//获取第一个包含类名的结点,即扩充抽象类
			if(args.equals("image")) {
	            classNode=nl.item(0).getFirstChild();
	            
			}
			//获取第二个包含类名的结点,即具体实现类
			else if(args.equals("os")) {
	            classNode=nl.item(1).getFirstChild();
			}
			
	        cName=classNode.getNodeValue();
	        //通过类名生成实例对象并将其返回
	        Class c=Class.forName(cName);
		  	Object obj=c.newInstance();
	        return obj;		
        }   
        catch(Exception e) {
            e.printStackTrace();
            return null;
        }
	}
}

单例模式

只能创建一个对象来使用

定义

Singleton 模式通常有两种实现形式。
第 1 种:懒汉式单例

​ 该模式的特点是类加载时没有生成单例,只有当第一次调用 getlnstance 方法时才去创建这个单例。

注意:如果编写的是多线程程序,则不要删除上例代码中的关键字 volatile 和 synchronized,否则将存在线程非安全的问题。如果不删除这两个关键字就能保证线程安全,但是每次访问时都要同步,会影响性能,且消耗更多的资源,这是懒汉式单例的缺点。

第 2 种:饿汉式单例
该模式的特点是类一旦加载就创建一个单例,保证在调用 getInstance 方法之前单例已经存在了。

饿汉式单例在类创建的同时就已经创建好一个静态的对象供系统使用,以后不再改变,所以是线程安全的,可以直接用于多线程而不会出现问题。

缺点

扩展不行,因为没有抽象类

LayzySingleton类(懒汉式单例)
class LayzySingleton{
	
	private static volatile LayzySingleton instance=null;
 
	private LayzySingleton (){

 }
	public static synchronized LayzySingleton getInstance(){
		if(instance==null){
			instance=new LayzySingleton();
		}
		return instance;
	}
 
 
}
HunrySingleton类(饿汉式单例(第一选择))
class HunrySingleton{
	//3.要求此对象也必须声明为static,这样方法才能调用,final能保证只赋值一次,可不加
	private static final HunrySingleton instance=new HunrySingleton();
	//1.私有化类的构造器
	private HunrySingleton(){
		
	}
	//2.提供公共的静态方法,返回类的对象
	public static HunrySingleton getInstance(){
		return instance;
	}
}
客户端
public static void main(String[] args) {
		
		HunrySingleton h1=HunrySingleton.getInstance();
		HunrySingleton h2=HunrySingleton.getInstance();
		System.out.println(h1==h2);
		
		LayzySingleton l1=LayzySingleton.getInstance();
		LayzySingleton l2=LayzySingleton.getInstance();
		System.out.println(l1==l2);
		
	}

true

true

装饰模式

定义

动态地给一个对象增加额外的职责,就增加功能来说,装饰模式比生成子类更加灵活

装饰(Decorator)模式的主要优点有:

  • 采用装饰模式扩展对象的功能比采用继承方式更加灵活。
  • 可以设计出多个不同的具体装饰类,创造出多个不同行为的组合。

其主要缺点是:装饰模式增加了许多子类,如果过度使用会使程序变得很复杂。

java中的流的使用

java中的图形化界面的使用

星巴克咖啡加调料 结算 问题

单品咖啡是被装饰者 调料是装饰者 两者都继承一个高层抽象类

装饰者 是继承加组合的关系把 被装饰者 引入

装饰模式的叠加(如一个咖啡加很多调料)是通过递归实现的

Drink类(component类)

被装饰的主体

public abstract class Drink {
	
	public String des;
	private float price=0.0f;
	public String getDes() {
		return des;
	}
	public void setDes(String des) {
		this.des = des;
	}
	public float getPrice() {
		return price;
	}
	public void setPrice(float price) {
		this.price = price;
	}
	//计算价格的抽象方法
	public abstract float cost();
}
Coffe类(被装饰类)
class Coffee extends Drink{

	@Override
	public float cost() {
		// TODO Auto-generated method stub
		return super.getPrice();
	}
	
}

//单品
class Espresso extends Coffee{

	public Espresso(){
		setDes(" 意大利咖啡");
		setPrice(6.0f);
	}
}
//单品
class LongBlack extends Coffee{

	public LongBlack(){
		setDes(" LongBlack");
		setPrice(5.0f);
	}
}
//单品
class ShortBlack extends Coffee{
	
	public ShortBlack(){
		setDes(" ShortBlack");
		setPrice(4.0f);
	}
}
Decorator类(装饰类)
public class Decorator extends Drink{

	private Drink obj;
	
	public Decorator(Drink obj){
		this.obj=obj;
	}
	
	public float cost(){
		//getprice为拿到调料自己的价格
		return super.getPrice()+obj.cost();
		
	}
	@Override
	public String getDes() {
		// TODO Auto-generated method stub
		// obj.getDes()输出被装饰者的信息
		return des + " " +getPrice()+ " && "+obj.getDes();
	}
}
Chocolate类等(具体的Decorator)
class Chocolate extends Decorator{
//具体的Decorator 调味品
	public Chocolate(Drink obj) {
		super(obj);
		setDes("巧克力");
		setPrice(3.0f);
	}
	
}
//具体的Decorator 调味品
class Milk extends Decorator{
	
	public Milk(Drink obj) {
		super(obj);
		setDes("牛奶");
		setPrice(2.0f);
	}
	
}
//具体的Decorator 调味品
class Soy extends Decorator{
	
	public Soy(Drink obj) {
		super(obj);
		setDes("豆浆");
		setPrice(1.5f);
	}
	
}
Test

//装饰模式订单 2份巧克力+一份牛奶的LongBlack
		
		//1.点一份LongBlack
		Drink order=new LongBlack();
		System.out.println("费用1= " +order.cost());
		System.out.println("描述1= " + order.getDes());
		
		//2.再加入一份牛奶
		order =new Milk(order);
		System.out.println("加入一份牛奶 费用= " +order.cost());
		System.out.println("加入一份牛奶 描述= " + order.getDes());
		
		//3.再加入一份巧克力
		order =new Chocolate(order);
		System.out.println("加入一份牛奶 加入一份巧克力 费用= " +order.cost());
		System.out.println("加入一份牛奶 加入一份巧克力 描述= " + order.getDes());
		
		//4.再加入一份巧克力
		order =new Chocolate(order);
		System.out.println("加入一份牛奶 加入2份巧克力 费用= " +order.cost());
		System.out.println("加入一份牛奶 加入2份巧克力 描述= " + order.getDes());
		
		/*显示
		         费用1= 5.0
				描述1=  LongBlack
				
				加入一份牛奶 费用= 7.0
				加入一份牛奶 描述= 牛奶 2.0 &&  LongBlack
				
				加入一份牛奶 加入一份巧克力 费用= 10.0
				加入一份牛奶 加入一份巧克力 描述= 巧克力 3.0 && 牛奶 2.0 &&  LongBlack
				
				加入一份牛奶 加入2份巧克力 费用= 13.0
				加入一份牛奶 加入2份巧克力 描述= 巧克力 3.0 && 巧克力 3.0 && 牛奶 2.0 &&  LongBlack*/

建造者模式

定义

:又叫做生成器模式,是一种对象创建模式,它可以将复杂对象的建造过程抽象出来(抽象类别),使这个抽象过程的不同实现方法可以构造出不同表现的对象

钩子方法

属于基本方法的一种,在指挥者中一般是isxxx();返回类型为Boolean

另一种深入变形是1. 将director去掉 ,将那个construction的方法放在抽象builder类中,有参

第二种可以称为模板方法的是2.将director去掉 ,将那个construction的方法放在抽象builder类中,无参

House类(产品)
//product产品
public class House {

	private String baise;
	private String wall;
	private String roofed;
	public String getBaise() {
		return baise;
	}
	public void setBaise(String baise) {
		this.baise = baise;
	}
	public String getWall() {
		return wall;
	}
	public void setWall(String wall) {
		this.wall = wall;
	}
	public String getRoofed() {
		return roofed;
	}
	public void setRoofed(String roofed) {
		this.roofed = roofed;
	}
	
}
HouseBuilder类(抽象建造者)

//抽象建造者
public abstract class HouseBuilder {
	protected House house=new House();

	//将建造流程写好
	public abstract void buildBasic();
	public abstract void buildWalls();
	public abstract void buildRoofed();
	
	//建造房子好后,将产品(房子)返回
	public House buildHouse(){
		return house;
		
	}
}
CommonHouse类(建造具体)
//普通房子
class CommonHouse extends  HouseBuilder{

	@Override
	public void buildBasic() {
		// TODO Auto-generated method stub
		System.out.println("普通房子打地基5米");
	}

	@Override
	public void buildWalls() {
		// TODO Auto-generated method stub
		System.out.println("普通房子砌墙10cm");
		
	}

	@Override
	public void buildRoofed() {
		// TODO Auto-generated method stub
		System.out.println("普通房子屋顶");
	}
	
}

//高楼
class HighBuilding extends  HouseBuilder{

	@Override
	public void buildBasic() {
		// TODO Auto-generated method stub
		System.out.println("高楼打地基100米");
	}

	@Override
	public void buildWalls() {
		// TODO Auto-generated method stub
		System.out.println("高楼砌墙20cm");
		
	}

	@Override
	public void buildRoofed() {
		// TODO Auto-generated method stub
		System.out.println("高楼透明屋顶");
	}
	
}
HouseDirector类(指挥者)
public class HouseDirector {

	HouseBuilder houseBuilder=null;
			
	//通过构造器传入housebuilder
	public HouseDirector(HouseBuilder houseBuilder) {
		super();
		this.houseBuilder = houseBuilder;
	}

	//通过setter 传入houseBilder
	public void setHouseBuilder(HouseBuilder houseBuilder) {
		this.houseBuilder = houseBuilder;
	}
	

	//如何建造房子的流程,交给指挥者
	public House constructHouse(){
		houseBuilder.buildBasic();
		houseBuilder.buildWalls();
		houseBuilder.buildRoofed();
		return houseBuilder.buildHouse();
	}
	
			
		
Cilent类
	public static void main(String[] args) {
		//盖普通房
		CommonHouse commonHouse=new CommonHouse();
		//准备创建房子的指挥者
		HouseDirector houseDirector=new HouseDirector(commonHouse);
		
		//完成盖房子。返回产品(房子)
		House house=houseDirector.constructHouse();
		
	}

适配器模式

适配器分有类适配器、对象适配器、接口适配器

类适配器

特点:继承被适配者 实现适配接口

缺点:继承使得耦合度增高

手机充电器例子

Voltage220v类
//适配的类
public class Voltage220v {

	//输出220v的电压
	public int outPut220v(){
		int src=220;
		System.out.println("电压="+ src + "伏");
		return src;
	}
}
Voltage5v类
//适配接口
public interface Voltage5v {
	//输出5v的电压
	public int outPut5v();
}

VoltageAdapter类
//适配器类
public class VoltageAapter extends Voltage220v implements Voltage5v {

	@Override
	public int outPut5v() {
		int srcV=outPut220v();
		int dstV=srcV/44;//转成5伏
		return dstV;
	}

}
Phone类
public class Phone {

	//充电
	public void charging(Voltage5v voltage5v){
		if(voltage5v.outPut5v()==5){
			System.out.println("电压为5v ,可以充电。");
		} else if(voltage5v.outPut5v()>5){
			System.out.println("电压大于5v ,无法充电。");
		}
	}
}

客户端
//类适配器模式
	public static void main(String[] args) {
		// TODO Auto-generated method stub

		Phone phone=new Phone();
		phone.charging(new VoltageAapter());
		System.out.println();
	}
//显示:
//电压=220伏
//电压为5v ,可以充电。

对象适配器

基本思路和类的适配器模式相同,只是将Adapter类作修改,不是继承src类(被适配),而是持有src类的实例

适配器与被适配者的继承关系改为组合关系

VoltageAdapter2类(替换)
//适配器类
public class VoltageAapter2 implements Voltage5v {

	@Override
    private Voltage220v voltage220v;//聚合
    //通过构造器传入被适配类
    public VoltageAapter2(Voltage220v voltage220v){
        this.voltage220v=voltage220v;
    }
	public int outPut5v() {
        int dstV=0;
        if(null != voltage220v){
          
           int srcV=voltage220v.outPut220v();//获取对象的方法
            dstV=srcV/44;//转成5伏
        }
		
		return dstV;
	}

}
客户端(替换)
//对象适配器模式
	public static void main(String[] args) {
		// TODO Auto-generated method stub

		Phone phone=new Phone();
		phone.charging(new VoltageAapter(new Voltage220v()));
		System.out.println();
	}

接口适配器

又称缺省适配器

当不需要使用接口的所有方法时,可以先设计一个抽象类实现接口,并为该接口中每个方法提供一个默认方法(空),那么该抽象类的子类可以有选择的通过覆盖父类方法来使用想要的方法。

ps://利用匿名内部类的抽象类可以创建实例的方法

关键

匿名内部类 抽象 接口

interface4类
public interface interface4 {

	public void m1();
	public void m2();
	public void m3();
	public void m4();
}
AbsAdapter类

//通过抽象方法空实现接口所有方法
public abstract class AbsAdapter implements interface4 {

	public void m1(){
		
	}
	public void m2(){
		
	}
	public void m3(){
		
	}
	public void m4(){
		
	}
}
客户端
	public static void main(String[] args) {
		//利用匿名内部类的抽象类可以创建实例的方法
		AbsAdapter absAdapter=new AbsAdapter() {
			//只需要覆盖我们需要使用的方法
			@Override
			public void m1() {
				System.out.println("使用了m1");
			}
		};
		absAdapter.m1();
	}

组合模式

定义

又叫 部分整体模式,它创建了对象组的树形结构,将对象组合成树状结构以表示“整体-部分”的层次关系

学校-学院-专业

调用时类似于图形化界面,将底层的先做好,然后一层层add到高层,调用时就可以选择哪方面的东西,如只看专业,只看某个学院等

OrganizationComponent抽象类(顶层)
public abstract class OrganizationComponent {

	private String name;//名字
	private String des;//描述
	public OrganizationComponent(String name, String des) {
		super();
		this.name = name;
		this.des = des;
	}
	protected void add(OrganizationComponent organizationComponent){
		//默认实现 因为有一些叶子节点是不需要实现的
	}
	protected void remove(OrganizationComponent organizationComponent){
		//默认实现 因为有一些叶子节点是不需要实现的
	}
	
	public String getName() {
		return name;
	}
	public void setName(String name) {
		this.name = name;
	}
	public String getDes() {
		return des;
	}
	public void setDes(String des) {
		this.des = des;
	}
	
	//打印 都有 抽象
	protected abstract void print();
}

University类(composite)

List organizationComponents=new ArrayList();是组合模式的关键;


//学校 就是composite这个角色 ,可以管理college
public class University extends OrganizationComponent {

	List<OrganizationComponent> organizationComponents=new ArrayList<OrganizationComponent>();
	//构造器
	public University(String name, String des) {
		super(name, des);
		// TODO Auto-generated constructor stub
	}

	//重新add
	@Override
	protected void add(OrganizationComponent organizationComponent) {
		// TODO Auto-generated method stub
		organizationComponents.add(organizationComponent);
	}
	
	//重写remove
	@Override
	protected void remove(OrganizationComponent organizationComponent) {
		// TODO Auto-generated method stub
		organizationComponents.remove(organizationComponent);
	}
	
	@Override
	public String getName() {
		// TODO Auto-generated method stub
		return super.getName();
	}
	
	@Override
	public String getDes() {
		// TODO Auto-generated method stub
		return super.getDes();
	}
	
	//输出学院
	@Override
	protected void print() {
		// TODO Auto-generated method stub
		System.out.println("----------------" +getName()+"-----------------------");
		//遍历organizationComponents
		for (OrganizationComponent organizationComponent : organizationComponents) {
			organizationComponent.print();
		}
	}

	
	
}

College类(同上)

院系

//学院
public class College  extends OrganizationComponent{
	//List中存放着department
	List<OrganizationComponent> organizationComponents=new ArrayList<OrganizationComponent>();
	//构造器
	public College(String name, String des) {
		super(name, des);
		// TODO Auto-generated constructor stub
	}

	//重新add
	@Override
	protected void add(OrganizationComponent organizationComponent) {
		// TODO Auto-generated method stub
		organizationComponents.add(organizationComponent);
	}
	
	//重写remove
	@Override
	protected void remove(OrganizationComponent organizationComponent) {
		// TODO Auto-generated method stub
		organizationComponents.remove(organizationComponent);
	}
	
	@Override
	public String getName() {
		// TODO Auto-generated method stub
		return super.getName();
	}
	
	@Override
	public String getDes() {
		// TODO Auto-generated method stub
		return super.getDes();
	}
	
	//输出系
	@Override
	protected void print() {
		// TODO Auto-generated method stub
		System.out.println("----------------" +getName()+"-----------------------");
		//遍历organizationComponents
		for (OrganizationComponent organizationComponent : organizationComponents) {
			organizationComponent.print();
		}
	}
}
Department类(同上)

专业,因为是最底层,即叶子所有不需要add和remove

public class Department extends OrganizationComponent{

	public Department(String name, String des) {
		super(name, des);
		// TODO Auto-generated constructor stub
	}
	//add,remove不需要,因为它是叶子节点

	@Override
	public String getName() {
		// TODO Auto-generated method stub
		return super.getName();
	}
	
	@Override
	public String getDes() {
		// TODO Auto-generated method stub
		return super.getDes();
	}
	
	@Override
protected void print() {
	// TODO Auto-generated method stub
	System.out.println(getName());
}
}
Client
public class Client {

	//从大到小
	public static void main(String[] args) {
		//学校
		OrganizationComponent university=new University("清华大学", "中国顶级");
		
		//学院
		OrganizationComponent computerCollege=new College("计算机学院", "计算机学院");
		OrganizationComponent educationCollege=new College("教育学院", "教育学院");
		
		//专业 系
		computerCollege.add(new Department("软件工程", "写软件"));
		computerCollege.add(new Department("网络工程", "写网络"));
		computerCollege.add(new Department("计算机科学与技术", "计算机科学与技术 老牌"));
		
		
		educationCollege.add(new Department("特殊教育", "小孩"));
		educationCollege.add(new Department("汉语", "教汉语"));

		//将两个学院加入到学校中
		university.add(computerCollege);
		university.add(educationCollege);
		
		//打印大学所有院校和专业
		university.print();
		/*----------------清华大学-----------------------
		----------------计算机学院-----------------------
		软件工程
		网络工程
		计算机科学与技术
		----------------教育学院-----------------------
		特殊教育
		汉语*/
		
		//打印专业
		computerCollege.print();

	}
}

迭代器模式

定义

提供一种方法顺序访问一个聚合对象中的各个元素,又不暴露该对象的内部表示

遍历一个学院和系

iterator 用于处理 处理数据 的方式

aggregate 用于存放数据或对数据的增加等等

College接口(属于聚集aggregate)
public interface College {


	public String getName();
	
	//增加系的方法
	public void addDepartment(String name,String desc);
	
	//返回一个迭代器。遍历
	public 	Iterator createIterator();
}

ComputerCollege类(具体aggregate实现类1)


public class ComputerCollege  implements College{

	Department[] departments;
	int numOfDepartment=0;//保存当前数组的对象个数
	
	public ComputerCollege(){
		departments=new Department[5];
		addDepartment("java", "java");
		addDepartment("php", "php");
		addDepartment("data", "data");
		addDepartment("python", "python");
	}
	
	@Override
	public String getName() {
		// TODO Auto-generated method stub
		return "计算机学院";
	}

	@Override
	public void addDepartment(String name, String desc) {
		// TODO Auto-generated method stub
		Department department=new Department(name, desc);
		departments[numOfDepartment]=department;
		numOfDepartment++;
	}

	@Override
	public Iterator createIterator() {
		// TODO Auto-generated method stub
		return new  ComputerCollegeIterator(departments);
	}

}
InfoCollege类(具体aggregate实现类2)
public class InfoCollege implements College{

	//list形式存放
	List<Department> departments;
	int numOfDepartment=0;//保存当前数组的对象个数
	
	public InfoCollege(){
		departments=new ArrayList<Department>();
		addDepartment("信息安全", "信息安全专业");
		addDepartment("网络安全", "网络安全专业");
		addDepartment("服务器安全", "服务器安全专业");
	}
	
	@Override
	public String getName() {
		// TODO Auto-generated method stub
		return "信息工程学院";
	}

	@Override
	public void addDepartment(String name, String desc) {
		// TODO Auto-generated method stub
		Department department=new Department(name, desc);
		departments.add(department);
	}

	@Override
	public Iterator createIterator() {
		// TODO Auto-generated method stub
		return new  InfoCollegeIterator(departments);
	}
}
ComputerCollegeIterator类(具体iterator实现类)
//Iterator是内部提供的接口
public class ComputerCollegeIterator implements Iterator{
 
	 
	//需要知道department是以怎么样的方式存储-》数组
	Department[] departments;
	int position=0;//遍历的位置
	
	public ComputerCollegeIterator(Department[] departments) {
		this.departments = departments;
	}

	//判断是否还有下一个元素
	@Override
	public boolean hasNext() {
		// TODO Auto-generated method stub
		if(position>=departments.length|| departments[position]==null){
			return false;
		}else{
			return true;
		}
	}

	//返回下一个元素
	@Override
	public Object next() {
		// TODO Auto-generated method stub
		Department department=departments[position];
		position++;
		return department;
	}
	//空实现
	public void remove(){
		
	}
	

	

}
InfoCollegeIterator类(具体iterator实现类)

public class InfoCollegeIterator implements Iterator {


	//需要知道department是以怎么样的方式存储-》List
	List<Department> departments;
	int index=-1;//索引,表示遍历到list的第几个
	
	public InfoCollegeIterator(List<Department> departments) {
		this.departments = departments;
	}

	//判断list是否还有下一个元素
	@Override
	public boolean hasNext() {
		// TODO Auto-generated method stub
		if(index>=departments.size()-1){
			return false;
		}else{
			index++;
			return true;
		}
	}

	//返回下一个元素
	@Override
	public Object next() {
		// TODO Auto-generated method stub
		return departments.get(index);
	}
	//空实现
	public void remove(){
		
	}
}

Department类(数据)
public class Department {

	private String name;
	private String desc;
	public Department(String name, String desc) {
		super();
		this.name = name;
		this.desc = desc;
	}
	public String getName() {
		return name;
	}
	public void setName(String name) {
		this.name = name;
	}
	public String getDesc() {
		return desc;
	}
	public void setDesc(String desc) {
		this.desc = desc;
	}
	
}

OutPutImp类(输出类)

public class OutPutImp {

	//拿到学院集合
	List<College> collegeList;

	public OutPutImp(List<College> collegeList) {
		this.collegeList = collegeList;
	}
	
	//遍历所有学院
	public void printCollege(){
		//取出collegeList 中 所有的学院,java的list已经实现了iterator这个接口
		Iterator<College> iterator =collegeList.iterator();
		while(iterator.hasNext()){
			College college=iterator.next();
			System.out.println("==="+college.getName()+"====");
			printDepartment(college.createIterator());
		}
	}
	
	//输出 学院输出系
	public void printDepartment(Iterator iterator){
		while(iterator.hasNext()){
			Department d=(Department) iterator.next();
			System.out.println(d.getName());
		}
	}
}
客户端
public class Client {

	public static void main(String[] args) {
		List<College> colleges=new ArrayList<College>();
		
		ComputerCollege computerCollege =new ComputerCollege();
		InfoCollege infoCollege=new InfoCollege();
		
		colleges.add(computerCollege);
		colleges.add(infoCollege);
		
		
		OutPutImp outPutImp=new OutPutImp(colleges);
		outPutImp.printCollege();
		/*===计算机学院====
				java
				php
				data
				python
				===信息工程学院====
				信息安全
				网络安全
				服务器安全*/

	}
}

外观模式

为子系统中的一组接口提供一个统一的入口。外观模式定义一个高层接口,这个接口使得这一子系统更加容易使用

public class Facade {

	
	private SubSystemA obj1=new SubSystemA();
			private SubSystemB obj2=new SubSystemB();
			private SubSystemC obj3=new SubSystemC();
			public void method() {
				obj1.methodA();
				obj2.methodB();
				obj3.methodC();
			}
			
			public static void main(String[] args) {
				Facade facad =new Facade();
				facad.method();
			}
}
class SubSystemA{
	public void methodA() {
		System.out.println("方法一");
	}
}
class SubSystemB{
	public void methodB() {
		System.out.println("方法二");
	}
}
class SubSystemC{
	public void methodC() {
		System.out.println("方法三");
	}
}

享元模式

定义

运用共享技术有效地支持大量细粒度的复用

目的

原型模式:减少类class的数量,用对象来代替类。  (这些对象内部属性一致)

享元模式:减少对象的数量

package flyweightstype;

import java.util.HashMap;

public abstract class FlyWeight {

	public abstract void operation(String extrinsicState);
	public static void main(String[] args) {
		FlyWeightFactory fwf=new FlyWeightFactory();
		FlyWeight fw=fwf.getFlyWeight("helloworld");
		fw.operation("红色");
		fw.operation("黄色");
		fw.operation("绿色");
		
		FlyWeight fw1=fwf.getFlyWeight("helloworld");
		fw1.operation("红色");
		fw1.operation("黄色");
		fw1.operation("绿色");
		
		FlyWeight fw2=fwf.getFlyWeight("hello design");
		fw2.operation("红色");
		fw2.operation("黄色");
		fw2.operation("绿色");
		
		
	}
}
 class ConcreteFlyWeight extends FlyWeight{

	 private String intrinsicState;
	 
	public ConcreteFlyWeight(String intrinsicState) {
		this.intrinsicState = intrinsicState;
	}

	@Override
	public void operation(String extrinsicState) {
System.out.println(intrinsicState+":"+extrinsicState);		
	}
	
}
  class UnsharedConcreteFlyWeight extends FlyWeight{

	@Override
	public void operation(String extrinsicState) {
		// TODO Auto-generated method stub
		
	}
	 
 }
  
  class FlyWeightFactory{
	  private HashMap flyHashMap=new HashMap();
	  public FlyWeight getFlyWeight(String key){
		  if(flyHashMap.containsKey(key)){
			  System.out.println("已经创建过了 key:::"+key);
			  return (FlyWeight)flyHashMap.get(key);
			  
		  }else {
			  FlyWeight fw=new ConcreteFlyWeight(key);
			  flyHashMap.put(key, fw);
			  return fw;
		  }
	  }
  }
/*helloworld:红色
helloworld:黄色
helloworld:绿色
已经创建过了 key:::helloworld
helloworld:红色
helloworld:黄色
helloworld:绿色
hello design:红色
hello design:黄色
hello design:绿色*/

代理模式

定义

给某一个对象提供一个代理或占位符,并由代理对象来控制对原对象的访问。

public abstract class  Subject{

    public abstract void  request();
}
public class RealSubject extends Subject{

    public  void  request(){
        //具体业务代码
    }
}
public class Proxy extends Subject{

    public void preRequest(){
        ....
    }
    
    private RealSubject realSubject=new RealSubject();
    public  void  request(){
        preRequest();
        realSubject.request();
        postRequest();
    }
    
    public void postRequest(){
        ....
    }
    
}

结构

远程代理

又称为大使

为一个位于不同地址空间的对象提供一个本地的代理对象,这个不同的地址空间可以在同一台主机,也可以在另一台主机中

虚拟代理

如果需要创建一个资源消耗较大的对象,先创建一个消耗较小的的对象来表示,真是对象只在需要的时候才被真正创建。

例图片缩略图

动态代理

普通代理

强制代理

优缺点

优点:

1.能够协调调用者和被调用者,降低了系统的耦合度

2.可针对抽象主题角色进行编程,增加代理类无须修改源代码

缺点:

1.有些类型的代理模式可能会造成请求的处理速度变慢

2.实现过程复杂

职责链模式

定义

客户无需关心请求细节,

不纯的职责链模式:java异常处理机制,还有早期java awt事件模型jdk1.0中叫做事件浮升,之后是观察者模式代替。在javascript仍然使用。

解释器模式

定义

给定一个语言,定义他的问法的一种表示,并定义一个解释器。这个解释器使用该表示来解释语言中的句子

中介者模型

定义

定义一个对象来封装一系列对象的交互。通过中介者去调用具体实现的行为,使其耦合松散。

具体的mediator类似于统一的加工厂,集合所有行为,给传进来的参数统一赋予行为。

状态模式

硬编码

定义

硬编码是将数据直接嵌入到程序或其他可执行对象的源代码中的软件开发实践,与从外部获取数据或在运行时生成数据不同。

释义

举个例子,比如说你做个软件,他有菜单栏,你如果把菜单的标题全部写在代码里,那如果现在要换英文的,你就不得不改变代码。
现在换一种方式,你把菜单标题全部写在一个文本里,比如叫title.txt,现在你要英文,那么只要把title.txt里面相对应的值换成英文就可以了。
不用在去该代码本身。

这就是 使用与配置相分离的概念
还有比如面向接口编程的概念,你可以去网上查,这都可以减少硬编码带来的后期维护

命令模式

1.类似于按钮和事件处理类的关系(其实是观察者模式)

2.发送者与接受者之间引入了新的命令对象(电线),两者完全解耦

3.命名模式相当于开关控制电灯或风扇之间的电线。

定义

将一个请求封装为一个对象,从而可用不同的请求对客户进行参数化,对请求排序或者记录请求日志,以及支持可撤销的操作。

关键

总结来说就是调用类中组合了继承了抽象的方法类(电灯风扇等等),方法类再组合具体操作(开关中档低档等)组合组合。类似于DAO command-》Invoker

实现命令队列

增加一个命令队列类 和调用类差不多 与调用中组合的方法改成容器类,通过加命名的方式存储,然后统一在执行类中逐个执行(循环),现在变成三组合了,command,commandQueue,Invoker,从左到右依次组合到右边的类中。

记录请求日志

每一步命名操作序列化写入日志文件中file

实现撤销操作

单一职责原则

定义

:就一个类而言,应该仅有一个引起它变化的原因

MVC 增删改查功能在DAO,数据在DTO,工具类在Util类中等

开放封闭原则

定义

:软件实体(类,模块,函数等)可以扩展,但不可以修改

关键

1:抽象化是开闭原则的关键:相对稳定的抽象层+灵活的具体层

2:对可变性封装原则-》找到系统的可变因素并将其封装起来

依赖倒转原则

定义

1:高层模块不应该依赖于底层模块,两个都应该依赖抽象

2:抽象不应该依赖细节,细节应该依赖抽象

方式

1:面向接口编程

2:通过依赖注入的方式(构造器注入,setter注入,接口注入)

里氏代换原则

定义

1:子类型必须能够替换掉他们的父类型

​ a:输入参数可以被放大,反之不行

​ b:输出结果可以被缩小,反之不行

2:子类必须完全实现父类的方法

迪米特法则

定义

又称最少知道原则

每一个软件单位对其他的单位都只有最少的知识,而且局限于那些与本单位密切相关的软件单位。

要求

只与直接的朋友通信

直接的朋友:成员变量,方法参数,方法返回值中的类为直接的朋友,而出现在局部变量的类不是(如一个方法中new一个其他类的对象变量引入)

效果

应用迪米特法则可降低系统的耦合度,使类与类之间保持松散的耦合关系

合成复用原则

定义

优先使用对象组合,而不是继承来达到复用的目的。

复用时要尽量使用组合/聚合关系(关联关系),少用继承。

(实际就是少用继承,多月引入新对象来调用方法)

A类与B类,父类B类可以通过设置A类型参数变量来调用A类方法

接口隔离原则

定义

:客户端不应该依赖那些它不需要的接口

GRASP模式/原则

​ 通用职责分配软件模式

定义

​ GRASP包含9种模式/原则,分别是信息专家、创建者、控制器、低耦合、高内聚、多态、纯虚构、间接性、防止变异

Java反射机制

forName(string className)可以返回与带有给定字符串名的类或接口相关联的class对象,再通过newInstance(方法创建此对象所表示的类的一个新实例。

即通过一个类名字字符串得到类的实例。

核心代码

class c=class.forName(“java.lang.string”);

object obj=c.newInstance;

return obj;
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值