前几天听了个CSDN的讲座,提到一个简单的面视题:用JAVA写加减乘除.....老师说满意的答案不仅要用到接口或者继承,最好还到设计模式.今天突然想起来,就写了一个...初学设计模式,发出来请大家指点一下.
接口:
package org.caculator.interfaces;public interface DoCaculation {
public void caculate(float a, float b);
}实现类:
package org.caculator.method;import org.caculator.interfaces.DoCaculation;public class MinusMethod implements DoCaculation {//乘法和加法的实现与次类相同
public MinusMethod(float a, float b) {
// TODO Auto-generated constructor stub
caculate(a, b);
} public void caculate(float a, float b) {
// TODO Auto-generated method stub
System.out.println(a - b);
}}代理类:
package org.caculator.proxy;import org.caculator.interfaces.DoCaculation;public class CaculationProxy {
DoCaculation doc; public CaculationProxy(DoCaculation doc) {
// TODO Auto-generated constructor stub
this.doc = doc;
}}运算:
package org.caculator.run;import org.caculator.method.MinusMethod;
import org.caculator.method.MultiplyMethod;
import org.caculator.method.PlusMethod;
import org.caculator.proxy.CaculationProxy;public class Caculation { /**
 * @param args
 */
public static void main(String[] args) {
// TODO Auto-generated method stub
CaculationProxy cp = new CaculationProxy(new MultiplyMethod(20, 10));
CaculationProxy cp2 = new CaculationProxy(new MinusMethod(20, 10));
CaculationProxy cp3 = new CaculationProxy(new PlusMethod(20, 10));
}}

解决方案 »

  1.   

    楼主还没有真正理解静态代理模式没错,代理主题角色内部包含有对真实主题角色的引用,你在CaculationProxy代理类中声明了DoCaculation doc 这部分没有问题, 这使得可以在任何时候操作真实主题对象。但是,代理模式另外重要的一点是,代理主题角色 提供一个与真实主题角色相同的接口,这使得可以在任何时候可以替代真实主体; 也就是代理主题角色和真实主题角色实现同一个接口楼主你的代码显然没有.正确的使用静态代理模式来修改你的代码,那就是修改你的代理类为如下:package org.caculator.proxy;import org.caculator.interfaces.DoCaculation;public class CaculationProxy implements DoCaculation 
        DoCaculation doc;    public CaculationProxy(DoCaculation doc) {
            // TODO Auto-generated constructor stub
            this.doc = doc;
        }    @Override
        public void caculate(float a, float b) {
            System.out.println(a - b);
        }}
    然后在测试运行类中就应该是这样了
    public class Caculation {    /**
         * @param args
         */
        public static void main(String[] args) {
            
            //将代理类的实例的引用赋值给抽象主题角色(这里是接口DoCaculation )
            DoCaculation cp = new CaculationProxy(new MultiplyMethod(20, 10));
            DoCaculation  cp2 = new CaculationProxy(new MinusMethod(20, 10));
            DoCaculation  cp3 = new CaculationProxy(new PlusMethod(20, 10));
        }}
    而且,楼主你这里的例子中代理类并没有在实现接口的方法中,相比真实主题角色类来说有何种区别,没有任何的意义.使用代理的主要目的,我觉得是对真实主题角色中的逻辑方法执行前和执行后进行其他附加的操作. 不然,代理模式的使用就没有任何意义了
      

  2.   

    不好意思 有点错误你还有个问题  就是代理类的属性中, 你包含的应该是真实主题角色类  MinusMethod 类型的变量而最好不要是接口DoCaculation类型;
     
      

  3.   

    看看 这个博客上的一篇关于静态代理的 你就明白了http://jzinfo.javaeye.com/blog/550558搞明白后可以看看动态代理
      

  4.   

    学习下代理,但代理好像是.net中的概念,java没有
      

  5.   

    为什么不是接口?看其他人写的也不是用接口呢..
    http://eneasy.javaeye.com/blog/174887
      

  6.   


    java也有啊  而且很广泛 框架中用到了很多这样的设计模式
      

  7.   

    不知你这里用的是什么模式,可能是我太无知,不知道有这个模式。学习一个模式首先要知道这个模式能为你做什么,模式都是针对特定问题的能用解决方法。比如,Proxy模式通常用来实现Lazy Load/Creation/Initialization和消息转发。先看看消息转发的例子:
    // Interface
    interface Calculator {
        public double calculate(String expression);
    }// Stub class
    class CalculatorStub implements Calculator {
        ...
        public double calculate(String expression) {
            return calculateOnRemoteMachine(expression); // 3. But, the calculation is performed on remote machine.
        }
        ...
    }// Client code
    class CalculatorClient {
        ...
        private void useCalculator() {
            Calculator calculator = factory.createCalculator(); // 1. The factory created an object of CalculatorStub class.
            double result = calculator.calculate("A very complex expression"); // 2. Ask the calculator to calculate a expression.
            ...
        }
        ...
    }这里本来有一个LocalCalculator类,它实现了Calculator接口,在本机完成运算。但是,后来由于计算任务太多,本机完成所有计算非常吃力,所以再添加一个本地桩,并替换工厂,这样,客户代码无需做任何改动,便可实现需求。
    再看看一个Lazy Load的例子:
    在一个阅读器系统中,当被阅读的文档相当大时,一次将所有页都载入肯定会造成很大的延迟。根据分析,完全可以使用Lazy Load手法作优化:// Interface
    interface Page {
        public void present();
    }// Stub class
    class PageStub implements Page {
        ...
        public void present() {
            if (!actualPageLoaded()) {
                loadActualPage();
            }
            presentActualPage();
        }
        ...
    }// Client code
    class View {
        ...
        public void present() {
            ...
            getCurrentPage()->present();
            ...
        }
        ...
    }
    可见,Proxy模式常用于后期优化,并且这种优化极其简单,而且对客户代码的影响也非常小。