- 浏览: 1699730 次
- 性别:
- 来自: 杭州699号
文章分类
最新评论
-
莫莫摸:
为什么不用dubbo
RCP数据传输模型回顾 -
大胡子爸爸:
String, Class 都实现了Serializable接 ...
RPC框架几行代码就够了 -
lss598018587:
谢谢大神分享,比起新手看复杂的dubbo框架还不如看大神的这一 ...
RPC框架几行代码就够了 -
15606915740:
你好,请问一下。<dubbo:consumer filt ...
Dubbo文档 -
joqk12345:
...
一些设计上的基本常识
在MeteorTL(http://www.meteortl.org)中,多处遇到需要按类型分派处理,如:BinaryOperatorHandler,UnaryOperatorHandler,PropertyHandler,OutputFormatter,StringSequence等,
以BinaryOperatorHandler为例:
当引擎遇到二元操作符会回调BinaryOperatorHandler进行求值,接口如下:
但有的操作符是重载的,
如:加号(+),在操作数为“数字”和“字符串”时要进行不同的操作,
1.最直接的实现方法是使用instanceof逐个判断,但其可扩展性极差,实现如下:
2.职责链模式,每个Handler持有下一个Handler的引用,实现如下:
3. 用一个包装类,注册相应类型的处理类,实现如下:
以BinaryOperatorHandler为例:
当引擎遇到二元操作符会回调BinaryOperatorHandler进行求值,接口如下:
public interface BinaryOperatorHandler extends OperatorHandler { // 传入操作数,返回求值结果 public Object doEvaluate(Object leftOperand, Object rightOperand) throws ExpressionException; }
但有的操作符是重载的,
如:加号(+),在操作数为“数字”和“字符串”时要进行不同的操作,
1.最直接的实现方法是使用instanceof逐个判断,但其可扩展性极差,实现如下:
public class AddBinaryOperatorHandler implements BinaryOperatorHandler { public Object doEvaluate(Object leftOperand, Object rightOperand) throws ExpressionException { if (leftOperand instanceof Integer && leftOperand instanceof Integer) return new Integer(((Integer)leftOperand).intValue() + ((Integer)rightOperand).intValue()); /* 如果要添加一个日期加法,就需要修改代码加入else if else if (leftOperand instanceof Date && leftOperand instanceof DateNumber) return new Date(((Date)leftOperand).getTime() + ((DateNumber)rightOperand).getTime());*/ else return String.valueOf(leftOperand) + String.valueOf(rightOperand); } }
2.职责链模式,每个Handler持有下一个Handler的引用,实现如下:
public abstract class BinaryOperatorHandlerChain implements BinaryOperatorHandler { private BinaryOperatorHandler nextHandler; protected BinaryOperatorHandler getNextHandler() { return nextHandler; } public void setNextHandler(BinaryOperatorHandler nextHandler) { this.nextHandler = nextHandler; } } public class IntegerAddBinaryOperatorHandler extends BinaryOperatorHandlerChain { public Object doEvaluate(Object leftOperand, Object rightOperand) throws ExpressionException { if (leftOperand instanceof Integer && leftOperand instanceof Integer) return new Integer(((Integer)leftOperand).intValue() + ((Integer)rightOperand).intValue()); return getNextHandler().doEvaluate(leftOperand, rightOperand); } } public class StringAddBinaryOperatorHandler extends BinaryOperatorHandlerChain { // @overwrite public void setNextHandler(BinaryOperatorHandler nextHandler) { throw new ConfigurationException("字符串相加为终结处理,不能有下一Handler!"); } public Object doEvaluate(Object leftOperand, Object rightOperand) throws ExpressionException { return String.valueOf(leftOperand) + String.valueOf(rightOperand); } }
3. 用一个包装类,注册相应类型的处理类,实现如下:
public class BinaryOperatorHandlerDispatcher implements BinaryOperatorHandler { private final Map matchHandlers; //类型为<BinaryOperandMatcher, BinaryOperatorHandler> private final BinaryOperatorHandler defaultHandler; public BinaryOperatorHandlerDispatcher(Map matchHandlers, BinaryOperatorHandler defaultHandler) { this.matchHandlers = matchHandlers; this.defaultHandler = defaultHandler; } public Object doEvaluate(Object leftOperand, Object rightOperand) throws ExpressionException { // 在集合中匹配相应类型的处理器 for (Iterator iterator = matchHandlers.entrySet().iterator(); iterator.hasNext();) { Map.Entry entry = (Map.Entry)iterator.next(); if (((BinaryOperandMatcher)entry.getKey()).isMatch(leftOperand, rightOperand)) return ((BinaryOperatorHandler)entry.getValue()).doEvaluate(leftOperand, rightOperand); } // 未找到相应类型的处理器则使用默认处理器 if (defaultHandler != null) return defaultHandler.doEvaluate(leftOperand, rightOperand); //否则抛出异常 throw new UnhandleException("没有找到相应处理类!"); } } public class BinaryOperandMatcher { private final Class leftOperandClass; private final Class rightOperandClass; public BinaryOperandMatcher(Class leftOperandClass, Class rightOperandClass) { this.leftOperandClass = leftOperandClass; this.rightOperandClass = rightOperandClass; } // 匹配操作数类型 public boolean isMatch(Object leftOperand, Object rightOperand) { return isMatchClass(leftOperand, leftOperandClass) && isMatchClass(rightOperand, rightOperandClass); } private boolean isMatchClass(Object operand, Class operandClass) { if (operandClass == null || operand == null) return operandClass == null && operand == null; return operandClass.isAssignableFrom(operand.getClass()); } } public class IntegerAddBinaryOperatorHandler implements BinaryOperatorHandler { public Object doEvaluate(Object leftOperand, Object rightOperand) throws ExpressionException { assert(leftOperand instanceof Integer && leftOperand instanceof Integer); return new Integer(((Integer)leftOperand).intValue() + ((Integer)rightOperand).intValue()); } } public class StringAddBinaryOperatorHandler implements BinaryOperatorHandler { public Object doEvaluate(Object leftOperand, Object rightOperand) throws ExpressionException { return String.valueOf(leftOperand) + String.valueOf(rightOperand); } }
评论
3 楼
wwlhp
2008-01-12
chain和dispatcher的思路是相同的,只是controlling handler对各种子类handler实例的组织结构不同而已。但都面临着一个问题,如何将子类handler实例注册到总控handler?
2 楼
javatar
2007-10-18
如果匹配方式稳定,用Dispatcher方式是比较好的选择,但职责链可以处理更多特殊情况,因为Handler类可以随时调用nextHandler进行处理。
1 楼
huangyh
2007-10-16
由具体的Handler负责返回下一个Handler,是不是不大合适,这样很容易出现循环链路。是不是用 BinaryOperatorHandlerDispatcher 来负责 Handler 顺序维护?
发表评论
-
以HTTL为例讲讲模块分包&领域模型&扩展框架
2011-10-09 20:08 16732注:该博客内容已加入 ... -
CommonTemplate增加HTML标签版语法外套
2008-09-09 10:33 2972CommonTemplate(http://www.commo ... -
CommonTemplate访问者设计思考
2008-09-03 10:45 1777经过多个版本的调整, CommonTemplate(http: ... -
CommonTemplate发布0.8.6版本
2008-08-26 20:49 1802CommonTemplate发布0.8.6版本 ... -
CommonTemplate发布0.8.5版本
2008-08-04 13:23 1895CommonTemplate发布0.8.5版本(2008-08 ... -
CommonTemplate加入代码生成器
2008-07-21 13:15 2242模板引擎经常被用于做代码生成, 为此, CommonTempl ... -
加入对YAML数据格式的支持
2008-07-01 12:41 4003CommonTemplate(http://www.commo ... -
嵌套注释语法思考
2008-06-29 14:40 4016主流的C/C++/Java/C#等语言,都将注释语法设计成不可 ... -
转:开源协议
2008-06-10 17:23 2221来源:网络 (1)Contrib ... -
CommonTemplate完成查看器Viewer.exe(及安装程序)
2008-06-04 15:12 1870完成查看器初始版本. 实现功能: 双击*.ctl文件, 自动读 ... -
CommonTemplate完成外部构建树或表达式接口
2008-05-31 11:01 1950CommonTemplate: http://www.comm ... -
CommonTemplate异常国际化完成
2008-05-26 11:48 1925周未把一个累活给干了, 就是异常信息的国际化. 总共有220多 ... -
CommonTemplate加入对无穷数的支持.
2008-05-23 11:07 2740用"*"号表示无穷数, 常在下标号中使用, ... -
CommonTemplate导出模板所需变量结构
2008-05-12 18:28 2260在velocity的邮件列表中收到下面的邮件: Simon G ... -
CommonTemplate完成$snatch指令
2008-05-06 09:20 1903CommonTemplate(http://www.commo ... -
关于CTE当前API无法支持从非引擎方式构建模板树
2008-04-28 17:20 1795因隐藏了模板树的实现, 现在CommonTemplate(ht ... -
CommonTemplate完成DEBUG单步调试
2008-04-21 09:56 2533CommonTemplate(http://www.commo ... -
CommonTemplate准备加入$breakpoint指令
2008-04-19 10:30 2204准备在CommonTemplate( http://www.c ... -
很高兴桂林兄加入CommonTemplate的开发
2008-04-05 20:49 2933桂林的blog: http://jasongreen.itey ... -
展开式序列实现
2008-03-31 22:47 2098现在CommonTemplate(http://www.com ...
相关推荐
随着新的请求类型被添加进来,条件分派器会逐渐变得庞大而笨拙。 2. 缺乏灵活性和可维护性。代码膨胀使得更改或维护逻辑变得困难。 为了改进代码结构,文档中提出了提取方法(Extract Method)的改进策略。提取...
- **动态加载Catlet**:Catlet是Mycat中的可插拔组件,可以动态加载并处理特定类型的SQL语句。 - **SQLJobHandler**:负责处理SQL任务的具体逻辑。 - **工作流程**: - 创建SQLJob对象,包含具体的SQL语句及其上...
本书讲解了装饰器的基本结构,以及如何利用装饰器来实现动态类型选择,如根据不同的输入动态选择不同的处理方式。 #### 迭代器:解耦算法与容器 迭代器模式是设计模式之一,用于顺序访问集合对象,而无需暴露其...
HMB风格的核心是消息总线,它作为系统中的连接件,负责消息的分派、传递、过滤以及处理结果的返回。消息总线的存在使得系统具有高度的扩展性和适应性,同时也为软件架构设计提供了一个统一的框架。 ##### 2.2 构件...
- **分类**:模式可以按解决的问题类型进行分类,如结构型模式、行为型模式和创建型模式。 3. **常用模式** - **从混沌到结构**:通过模式的应用,可以从无序的状态构建出有序的系统结构。 - **分布式基础设施**...
15. **中间人(Middle Man)**:如果一个类大部分方法都是简单的分派,可能需要去除这个中间层,直接连接调用者和实际执行者。 16. **不适当的亲密关系(Inappropriate Intimacy)**:类之间过度交互,破坏了封装。限制...
5.6.4 断开项目与CVS的连接或为项目重分派一个CVS资源库..... 154 5.7 练习概述...... 154 5.8 本章小结...... 155 5.9 参考文献...... 155 第6章 Eclipse环境管理 157 6.1 Eclipse安装实例概览...... 158 6.1.1 ...
- **详细解析**:给定二叉树的前序遍历和中序遍历序列,可以通过一定的算法来重构该二叉树,并进而得出其后序遍历的结果。在本例中,根据给定的前序遍历`ABDEGCFH`和中序遍历`DBGEACHF`,可以推导出后序遍历结果为`...
5.6.4 断开项目与CVS的连接或为项目重分派一个CVS资源库..... 154 5.7 练习概述...... 154 5.8 本章小结...... 155 5.9 参考文献...... 155 第6章 Eclipse环境管理 157 6.1 Eclipse安装实例概览...... ...
5.6.4 断开项目与CVS的连接或为项目重分派一个CVS资源库..... 154 5.7 练习概述...... 154 5.8 本章小结...... 155 5.9 参考文献...... 155 第6章 Eclipse环境管理 157 6.1 Eclipse安装实例概览...... ...
在真正可复用的面向对象编程中,GoF 的《设计模式》为我们提供了一套可复用的面向对象技术,再配合 Refactoring(重构方法), 所以很少存在简单重复的工作,加上Java 代码的精炼性和面向对象纯洁性(设计模式是 java 的...