zoukankan      html  css  js  c++  java
  • 模式-“里氏替换原则”

    里氏替换原则是,同组的有类的两个子类,在使用子类A这个地方(方法/属性)您可以使用子类
    B代替.对于面向接口编程,我只需要确保同样的行为代码;基类的所有子类必须全部
    实现,换过来,子类的方法基类不一定都有;

    如果:有一个基类Base;其子类是Concrete;那么method(Base b)的调用能够转换成
    method(Concrete c);
    策略模式:一般,我们把解决某个问题的方法称为一个"算法",而把解决一类问题的算法封装
    成一个接口,那么实现算法的多种方式作为子类;在某个时候,在调用中我们使用算法A替换
    算法B,这就是策略模式在里氏代换原则中的应用;
    ***************策略模式************************************
    >准备一组算法,并将每个封装起来使的他们能够互换.

    Context   

    /**
     * 	@author Lean  @date:2014-10-17  
     */
    public class Context {
    
    	public static Strategy strategy;
    	
    	public static void main(String[] args) {
    		strategy=new ConcreteStrategyA();
    		strategy.calculate();
    	}
    	
    }
    
    abstract class Strategy{
    	
    	public abstract void calculate();
    	
    }
    
    class ConcreteStrategyA extends Strategy{
    
    	@Override
    	public void calculate() {
    		System.out.println("ConcreteStrategyA is called !");
    	}
    	
    }
    
    class ConcreteStrategyB extends Strategy{
    	
    	@Override
    	public void calculate() {
    		System.out.println("ConcreteStrategyB is called !");
    	}
    	
    


    IChoiceStrategy

    /**
     * 		选择策略
     * 
     * 	@author Lean  @date:2014-10-17  
     */
    public abstract class IChoiceStrategy {
    
    	/**
    	 * @return	返回列表名字
    	 */
    	public abstract String[] getNames();
    	
    	/**
    	 * @return	返回相应码
    	 */
    	public abstract int getCode(String name);
    	
    }
    

    /**
     * 	@author Lean  @date:2014-10-17  
     */
    public class SortChoiceStrategy extends IChoiceStrategy {
    	
    	private HashMap<String, Integer> mSortMap;
    	public String name;
    	
    	public SortChoiceStrategy() {
    		initSortMap();
    	}
    
    	private void initSortMap() {
    		mSortMap=new HashMap<String, Integer>();
    		mSortMap.put("最新上架", 0);
    		mSortMap.put("销量最高", 1);
    		mSortMap.put("价格最高", 2);
    		mSortMap.put("价格最低", 3);
    		name="最新上架";
    	}
    
    	@Override
    	public String[] getNames() {
    		Set<String> set=mSortMap.keySet();
    		Object[] tempObj=set.toArray();
    		String[] result=new String[tempObj.length];
    		for (int i = 0; i < tempObj.length; i++) {
    			result[i]=(String) tempObj[i];
    		}
    		return result;
    	}
    
    	@Override
    	public int getCode(String name) {
    		return mSortMap.get(name);
    	}
    
    }
    

    /**
     * 	@author Lean  @date:2014-10-17  
     */
    public class StatusChoiceStrategy extends IChoiceStrategy {
    	
    	private HashMap<String, Integer> mStatusMap;
    	public String name;
    	
    	public StatusChoiceStrategy() {
    		initStatusMap();
    	}
    	
    	private void initStatusMap() {
    		mStatusMap=new HashMap<String, Integer>();
    		mStatusMap.put("定制中", 1);
    		mStatusMap.put("已完毕", 2);
    		name="定制中";
    	}
    
    	@Override
    	public String[] getNames() {
    		Set<String> set=mStatusMap.keySet();
    		Object[] tempObj=set.toArray();
    		String[] result=new String[tempObj.length];
    		for (int i = 0; i < tempObj.length; i++) {
    			result[i]=(String) tempObj[i];
    		}
    		return result;
    	}
    
    	@Override
    	public int getCode(String name) {
    		return mStatusMap.get(name);
    	}
    
    }
    
    ***********************************************************

    代理模式:代理和被代理对象相同拥有一样的行为,我们把它封装成一个接口,那么,在被
    代理对象被调用的地方都能够使用代理对象替换以隐藏实现细节;
    ***************代理模式************************************
    如果一个场景,A想去买票,但A没时间,于是A托B到电影院帮他买票;
    换成面向对象思维:如果有一个对象A,和一个新的对象C,如今C想使用对象A,而A临时还
    不符合C的要求,这时能够间接的使用B以达到使用A的目的,同一时候,B又能够对使用过程进行

    拦截,如打印日志;(像这样的利用中间层来达到目的的模式还有适配器模式)

    /**
     * 	@author Lean  @date:2014-10-17  
     */
    public abstract class IPerson {
    	
    	public abstract void buyTicket();
    	
    }
    

    /**
     * 	@author Lean  @date:2014-10-17  
     */
    public class RealSeePerson extends IPerson {
    
    	@Override
    	public void buyTicket() {
    		System.out.println("RealSeePerson get the ticket !");
    	}
    
    }
    

    /**
     * 	@author Lean  @date:2014-10-17  
     */
    public class BuyTicketPerson extends IPerson{
    	
    	public RealSeePerson target;
    	
    	private void preBuyTicket(){
    		//TODO do th. before buy ticket
    		target=new RealSeePerson();
    	}
    	
    	@Override
    	public void buyTicket() {
    		preBuyTicket();
    		if (target!=null) {
    			target.buyTicket();
    		}
    		postBuyTicket();
    	}
    	
    	public void postBuyTicket(){
    		//TODO do th. after buy thicket
    	}
    	
    }
    

    >代理和被代理对象实现共同接口,代理对象被调用时调用被代理对象的托付;

    动态代理实现监听:

    /**
     * 	@author Lean  @date:2014-10-17  
     */
    public class VectorProxy implements InvocationHandler {
    	
    	private Object proxyobj;
    	
    	public VectorProxy(Object obj) {
    		proxyobj=obj;
    	}
    	
    	public static Object factor(Object obj){
    		Class cls=obj.getClass();
    		return Proxy.newProxyInstance(cls.getClassLoader(),cls.getInterfaces(),new VectorProxy(obj));
    	}
    	
    	@Override
    	public Object invoke(Object proxy, Method method, Object[] args)
    			throws Throwable {
    		System.out.println("method:"+method.getName());
    		if (args!=null) {
    			for (int i = 0; i < args.length; i++) {
    				System.out.println(args[i]+"");
    			}
    		}
    		//反射调用
    		Object obj=method.invoke(proxyobj, args);
    		System.out.println("*********");
    		return obj;
    	}
    	
    	public static void main(String[] args) {
    		List v=null;
    		//返回代理对象,并调用代理对象的add方法
    		v=(List) factor(new Vector(10));
    		v.add("New");
    	}
    	
    
    }
    
    ***********************************************************

    合成模式:上面两中模式都是里氏代换原则在方法方面的应用.合成模式使用树结果描写叙述
    总体和部分的关系,由于单纯元素和复合元素相同实现抽象,那么在抽象使用的地方,
    都能够这2种元素替代;
    ***************合成模式************************************

    合成模式分为透明式和安全式

    透明:指抽象接口声明了枝叶全部的全部接口方法,在叶子类中。对该方法进行空实现;

    /**
     * 	@author Lean  @date:2014-10-20  
     */
    public interface Component {
    	
    	void sampleOperation();
    
    	Composite getComposite();
    	
    	void add(Component component);
    	
    	void remove(Component component);
    	
    	Enumeration<Component> components();
    	
    }
    
    /**
     * 	@author Lean  @date:2014-10-20  
     */
    public class Composite implements Component {
    	
    	private Vector<Component> componentVector=new Vector<Component>();
    	
    	@Override
    	public Composite getComposite() {
    		return this;
    	}
    
    	@Override
    	public void sampleOperation() {
    		Enumeration<Component> enumeration=components();
    		while (enumeration.hasMoreElements()) {
    			Component component = (Component) enumeration.nextElement();
    			component.sampleOperation();
    		}
    	}
    
    	@Override
    	public void add(Component component) {
    		componentVector.addElement(component);
    	}
    
    	@Override
    	public void remove(Component component) {
    		componentVector.removeElement(component);
    	}
    
    	@Override
    	public Enumeration<Component> components() {
    		return componentVector.elements();
    	}
    
    }
    
    /**
     * 	@author Lean  @date:2014-10-20  
     */
    public class Leaf implements Component {
    
    	@Override
    	public Composite getComposite() {
    		return null;
    	}
    
    	@Override
    	public void sampleOperation() {
    		System.out.println(" call leaf here !");
    	}
    
    	@Override
    	public void add(Component component) {
    		
    	}
    
    	@Override
    	public void remove(Component component) {
    		
    	}
    
    	@Override
    	public Enumeration<Component> components() {
    		return null;
    	}
    
    }
    

    安全:指抽象接口仅仅声明叶子全部的方法,树枝类除了继承还包含了自己的管理叶子类方法;典型应用:Android的View,ViewGroup

    /**
     * 	@author Lean  @date:2014-10-20  
     */
    public interface Component {
    
    	Composite getComposite();
    	
    	void sampleOperation();
    	
    }
    
    /**
     * 	@author Lean  @date:2014-10-20  
     */
    public class Composite implements Component {
    	
    	private Vector componentVector=new Vector();
    	
    	@Override
    	public void sampleOperation() {
    		Enumeration enumeration=components();
    		while (enumeration.hasMoreElements()) {
    			((Component) enumeration.nextElement()).sampleOperation();
    		}
    	}
    
    	@Override
    	public Composite getComposite() {
    		return this;
    	}
    	
    	public Enumeration components(){
    		return componentVector.elements();
    	}
    	
    	public void add(Component component){
    		componentVector.addElement(component);
    	}
    	
    	public void remove(Component component){
    		componentVector.removeElement(component);
    	}
    	
    }
    
    /**
     * 	@author Lean  @date:2014-10-20  
     */
    public class Leaf implements Component {
    
    	@Override
    	public Composite getComposite() {
    		return null;
    	}
    
    	@Override
    	public void sampleOperation() {
    		System.out.println("leaf is called !");
    	}
    
    }
    

    由于分支机构基本继承抽象类,在抽象方法只支持类,那里可以换成一个叶子。例如,在安全模式。叶类可以换成棒/多叶;在透明模式下可以互换。这是与里氏代换原则;

    ***********************************************************


  • 相关阅读:
    Spring dispatcherServlet
    Tomcat tomcat-users.xml详解
    Tomcat server.xml详解
    WAR包
    Tomcat 部署
    Tomcat 使用说明
    Java sun的JDK
    Spring 使用中的设计模式
    缓存插件 EHCache 对象缓存(Spring)
    缓存插件 EHCache 页面缓存CachingFilter
  • 原文地址:https://www.cnblogs.com/yxwkf/p/4619449.html
Copyright © 2011-2022 走看看