①执行加减乘除运算
②日志:在程序执行期间追踪正在发生的活动
ArithmeticCalculator.java
public interface ArithmeticCalculator {
double add(double a, double b);
double sub(double a, double b);
double mul(double a, double b);
double div(double a, double b);
}
ArithmeticCalculatorImpl.java
public class ArithmeticCalculatorImpl implements ArithmeticCalculator {
@Override
public double add(double a, double b) {
return a + b;
}
@Override
public double sub(double a, double b) {
return a - b;
}
@Override
public double mul(double a, double b) {
return a * b;
}
@Override
public double div(double a, double b) {
return a / b;
}
}
ArithmeticCalculatorImpl.java
public class ArithmeticCalculatorImpl implements ArithmeticCalculator {
@Override
public double add(double a, double b) {
System.out.println("The method add begins with [" + a + ", " + b + "]");
double result = a + b;
System.out.println("The method add ends with " + result);
return result;
}
@Override
public double sub(double a, double b) {
System.out.println("The method sub begins with [" + a + ", " + b + "]");
double result = a - b;
System.out.println("The method sub ends with " + result);
return result;
}
@Override
public double mul(double a, double b) {
System.out.println("The method sub begins with [" + a + ", " + b + "]");
double result = a * b;
System.out.println("The method sub ends with " + result);
return result;
}
@Override
public double div(double a, double b) {
System.out.println("The method sub begins with [" + a + ", " + b + "]");
double result = a / b;
System.out.println("The method sub ends with " + result);
return result;
}
}
①代码混乱:越来越多的非业务需求(日志和验证等)加入后,原有的业务方法急剧膨胀。每个方法在处理核心逻辑的同时还必须兼顾其他多个关注点。
②代码分散: 以日志需求为例,只是为了满足这个单一需求,就不得不在多个模块(方法)里多次重复相同的日志代码。如果日志需求发生变化,必须修改所有模块。
代理设计模式的原理:使用一个代理将原本对象包装起来,然后用该代理对象”取代”原始对象。任何对原始对象的调用都要通过代理。代理对象决定是否以及何时将方法调用转到原始对象上。
CalculatorLoggingHandler.java
public class CalculatorLoggingHandler implements InvocationHandler {
private Object target;
public CalculatorLoggingHandler(Object target) {
this.target = target;
}
@Override
public Object invoke(Object proxy, Method method, Object[] args) throws Throwable {
System.out.println("The method " + method.getName() + "() begins with " + Arrays.toString(args));
Object result = method.invoke(target, args);
System.out.println("The method " + method.getName() + "() ends with " + result);
return result;
}
public static Object createProxy(Object target) {
return Proxy.newProxyInstance(target.getClass().getClassLoader(),
target.getClass().getInterfaces(),
new CalculatorLoggingHandler(target));
}
}
Main.java
public class Main {
public static void main(String[] args) {
ArithmeticCalculatorImpl arithmeticCalculator = new ArithmeticCalculatorImpl();
ArithmeticCalculator proxy = (ArithmeticCalculator) CalculatorLoggingHandler.createProxy(arithmeticCalculator);
System.out.println(proxy.add(12, 13));
}
}
The method add() begins with [12.0, 13.0]
The method add() ends with 25.0
25.0