- 浏览: 669270 次
- 性别:
- 来自: 北京
文章分类
- 全部博客 (233)
- mysql (20)
- tomcat (17)
- log4j (4)
- jdbc (2)
- hibernate (7)
- highcharts (10)
- java (27)
- bat (5)
- html (18)
- xampp (6)
- apache (9)
- Spring (3)
- windows (13)
- js (38)
- jquery (10)
- struts (20)
- json (1)
- css (7)
- 浏览器 (5)
- ASCII码表 (1)
- svn (3)
- 正则表达式 (3)
- vb (1)
- jsp (4)
- xml (2)
- C语言 (1)
- dll (1)
- 数据库 (8)
- 随便写 (19)
- WebService (1)
- Linux (1)
- 云计算 (2)
- HTTP (2)
- 音楽 (1)
- eclipse (2)
- JFreeChart (1)
- jnative (1)
- ant (1)
- WordPress (1)
- JavaEE (1)
- tag (1)
- ognl (1)
- 设计模式 (3)
- sql (2)
- office (5)
- 软件 (6)
- 健身 (18)
- php (2)
- 读书 (4)
- 管理 (1)
- sublime text (2)
- angularJS (1)
最新评论
-
资深菜鸟程序员:
正解 当中,你是最早的,你转载的那篇已经消失了,所以你就是最吊 ...
程序包com.sun.image.codec.jpeg不存在 -
jun1022509040:
http://download.csdn.net/detail ...
C3P0错误APPARENT DEADLOCK!!!解决 -
alafighting:
厉害!膜拜了~
程序包com.sun.image.codec.jpeg不存在 -
darrenzhong:
c3p0 报错APPARENT DEADLOCK!!! 解决方 ...
C3P0错误APPARENT DEADLOCK!!!解决 -
tslihejun:
谢谢,解决了我的问题。
highcharts 大量数据下y轴值精度丢失的解决
文章转自:http://tech.ddvip.com
S.O.L.I.D五大原则之OCP(开闭原则)
开闭原则的描述如下:
Software entities (classes, modules, functions, etc.) should be open for extension but closed for modification.
软件实体(类,模块,方法等等)应当对扩展开放,对修改关闭,即软件实体应当在不修改的前提下扩展。
open for extension(对扩展开放)的意思是说当新需求出现的时候,可以通过扩展现有模型达到目的。而Close for modification(对修改关闭)的意思是说不允许对该实体做任何修改,说白了,就是这些需要执行多样行为的实体应该设计成不需要修改就可以实现各 种的变化,坚持开闭原则有利于用最少的代码进行项目维护。
问题代码
为了直观地描述,我们来举个例子演示一下,下属代码是动态展示question列表的代码(没有使用开闭原则)。
上面的代码,view对象里包含一个render方法用来展示question列表,展示的时候根据不同的question类型使用不同的展示方 式,一个question包含一个label和一个问题类型以及choices的选项(如果是选择类型的话)。如果问题类型是Choice那就根据选项生 产一个下拉菜单,如果类型是Input,那就简单地展示input输入框。
该代码有一个限制,就是如果再增加一个question类型的话,那就需要再次修改renderQuestion里的条件语句,这明显违反了开闭原则。
重构代码
上面的代码里应用了一些技术点,我们来逐一看一下:
首先,questionCreator方法的创建,可以让我们使用模板方法模式将处理问题的功能delegat给针对每个问题类型的扩展代码renderInput上。
其次,我们用一个私有的spec属性替换掉了前面question方法的构造函数属性,因为我们封装了render行为进行操作,不再需要把这些属性暴露给外部代码了。
第三,我们为每个问题类型创建一个对象进行各自的代码实现,但每个实现里都必须包含renderInput方法以便覆盖questionCreator方法里的renderInput代码,这就是我们常说的策略模式。
通过重构,我们可以去除不必要的问题类型的枚举AnswerType,而且可以让choices作为choiceQuestionCreator函数的必选参数(之前的版本是一个可选参数)。
总结
重构以后的版本的view对象可以很清晰地进行新的扩展了,为不同的问题类型扩展新的对象,然后声明questions集合的时候再里面指定类型就行了,view对象本身不再修改任何改变,从而达到了开闭原则的要求。
另:懂C#的话,不知道看了上面的代码后是否和多态的实现有些类似?其实上述的代码用原型也是可以实现的,大家可以自行研究一下。
注:五大原则分别是:
The Single Responsibility Principle(单一职责SRP)
The Open/Closed Principle(开闭原则OCP)
The Liskov Substitution Principle(里氏替换原则LSP)
The Interface Segregation Principle(接口分离原则ISP)
The Dependency Inversion Principle(依赖反转原则DIP)
S.O.L.I.D五大原则之OCP(开闭原则)
开闭原则的描述如下:
Software entities (classes, modules, functions, etc.) should be open for extension but closed for modification.
软件实体(类,模块,方法等等)应当对扩展开放,对修改关闭,即软件实体应当在不修改的前提下扩展。
open for extension(对扩展开放)的意思是说当新需求出现的时候,可以通过扩展现有模型达到目的。而Close for modification(对修改关闭)的意思是说不允许对该实体做任何修改,说白了,就是这些需要执行多样行为的实体应该设计成不需要修改就可以实现各 种的变化,坚持开闭原则有利于用最少的代码进行项目维护。
问题代码
为了直观地描述,我们来举个例子演示一下,下属代码是动态展示question列表的代码(没有使用开闭原则)。
// 问题类型 var AnswerType = { Choice: 0, Input: 1 }; // 问题实体 function question(label, answerType, choices) { return { label: label, answerType: answerType, choices: choices // 这里的choices是可选参数 }; } var view = (function () { // render一个问题 function renderQuestion(target, question) { var questionWrapper = document.createElement('div'); questionWrapper.className = 'question'; var questionLabel = document.createElement('div'); questionLabel.className = 'question-label'; var label = document.createTextNode(question.label); questionLabel.appendChild(label); var answer = document.createElement('div'); answer.className = 'question-input'; // 根据不同的类型展示不同的代码:分别是下拉菜单和输入框两种 if (question.answerType === AnswerType.Choice) { var input = document.createElement('select'); var len = question.choices.length; for (var i = 0; i < len; i++) { var option = document.createElement('option'); option.text = question.choices[i]; option.value = question.choices[i]; input.appendChild(option); } } else if (question.answerType === AnswerType.Input) { var input = document.createElement('input'); input.type = 'text'; } answer.appendChild(input); questionWrapper.appendChild(questionLabel); questionWrapper.appendChild(answer); target.appendChild(questionWrapper); } return { // 遍历所有的问题列表进行展示 render: function (target, questions) { for (var i = 0; i < questions.length; i++) { renderQuestion(target, questions[i]); }; } }; })(); var questions = [ question('Have you used tobacco products within the last 30 days?', AnswerType.Choice, ['Yes', 'No']), question('What medications are you currently using?', AnswerType.Input) ]; var questionRegion = document.getElementById('questions'); view.render(questionRegion, questions);
上面的代码,view对象里包含一个render方法用来展示question列表,展示的时候根据不同的question类型使用不同的展示方 式,一个question包含一个label和一个问题类型以及choices的选项(如果是选择类型的话)。如果问题类型是Choice那就根据选项生 产一个下拉菜单,如果类型是Input,那就简单地展示input输入框。
该代码有一个限制,就是如果再增加一个question类型的话,那就需要再次修改renderQuestion里的条件语句,这明显违反了开闭原则。
重构代码
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd"> <html xmlns="http://www.w3.org/1999/xhtml"> <head> <meta http-equiv="Content-Type" content="text/html; charset=gb2312" /> <title>无标题文档</title> </head> <body> <div id="questions"> </div> <script type="text/javascript"> function questionCreator(spec, my) { var that = {}; my = my || {}; my.label = spec.label; my.renderInput = function() { throw "not implemented"; }; that.render = function(target) { var questionWrapper = document.createElement('div'); questionWrapper.className = 'question'; var questionLabel = document.createElement('div'); questionLabel.className = 'question-label'; var label = document.createTextNode(spec.label); questionLabel.appendChild(label); var answer = my.renderInput(); questionWrapper.appendChild(questionLabel); questionWrapper.appendChild(answer); return questionWrapper; }; return that; } function choiceQuestionCreator(spec) { var my = {}, that = questionCreator(spec, my); my.renderInput = function() { var input = document.createElement('select'); var len = spec.choices.length; for (var i = 0; i < len; i++) { var option = document.createElement('option'); option.text = spec.choices[i]; option.value = spec.choices[i]; input.appendChild(option); } return input; }; return that; } function inputQuestionCreator(spec) { var my = {}, that = questionCreator(spec, my); my.renderInput = function() { var input = document.createElement('input'); input.type = 'text'; return input; }; return that; } var view = { render: function(target, questions) { for (var i = 0; i < questions.length; i++) { target.appendChild(questions[i].render()); } } }; var questions = [ choiceQuestionCreator({ label: 'Have you used tobacco products within the last 30 days?', choices: ['Yes', 'No'] }), inputQuestionCreator({ label: 'What medications are you currently using?' }) ]; var questionRegion = document.getElementById('questions'); view.render(questionRegion, questions); </script> </body> </html>
上面的代码里应用了一些技术点,我们来逐一看一下:
首先,questionCreator方法的创建,可以让我们使用模板方法模式将处理问题的功能delegat给针对每个问题类型的扩展代码renderInput上。
其次,我们用一个私有的spec属性替换掉了前面question方法的构造函数属性,因为我们封装了render行为进行操作,不再需要把这些属性暴露给外部代码了。
第三,我们为每个问题类型创建一个对象进行各自的代码实现,但每个实现里都必须包含renderInput方法以便覆盖questionCreator方法里的renderInput代码,这就是我们常说的策略模式。
通过重构,我们可以去除不必要的问题类型的枚举AnswerType,而且可以让choices作为choiceQuestionCreator函数的必选参数(之前的版本是一个可选参数)。
总结
重构以后的版本的view对象可以很清晰地进行新的扩展了,为不同的问题类型扩展新的对象,然后声明questions集合的时候再里面指定类型就行了,view对象本身不再修改任何改变,从而达到了开闭原则的要求。
另:懂C#的话,不知道看了上面的代码后是否和多态的实现有些类似?其实上述的代码用原型也是可以实现的,大家可以自行研究一下。
注:五大原则分别是:
The Single Responsibility Principle(单一职责SRP)
The Open/Closed Principle(开闭原则OCP)
The Liskov Substitution Principle(里氏替换原则LSP)
The Interface Segregation Principle(接口分离原则ISP)
The Dependency Inversion Principle(依赖反转原则DIP)
发表评论
-
JQuery中的offset()
2014-12-02 13:56 916obj.offset().left 和 obj.off ... -
angularJS 中的逻辑form
2014-10-20 18:50 976angularJS中可以针对form表单进行校验,例如 ... -
JQuery简单的键盘事件
2014-09-05 11:11 1017//键盘操作 $(document).keydow ... -
浅谈Javascript 中几种克隆(clone)方式(转)
2014-06-11 16:09 787一:在Javascript里,如果克隆对象是基本类型,我们 ... -
JS通用事件绑定和移除程序
2014-04-30 08:53 1324首先判断是否可使用DOM2级方法,然后判断是否可使用 ... -
JS执行环境
2014-04-29 18:21 1721全局执行环境是window对象,因此所有全局变量和函数都是作 ... -
JS命名空间
2014-04-29 17:26 766空间的定义 以下片段定义了一个名为CM的空间 (f ... -
respond.js在IE下不工作
2014-03-07 14:15 1542找了半天原因,最后发现原来是respond.js和boots ... -
文档声明<!DOCTYPE html>导致document.body.offsetHeight取值为0
2014-03-03 13:36 1117关于通过JS获取窗口高度和宽度的问题,如果使用了文档声 ... -
获取父框架iframe的ID
2013-07-22 09:04 1033获取父框架iframe的ID var frameId = wi ... -
highcharts 取得y轴的最大最小值
2013-07-17 14:30 4574highcharts的y轴可以指定最大最小值,如果不指定则由h ... -
Jquery.LazyLoad.js插件修正版下载,实现图片延迟加载特效【转】
2013-03-04 09:29 1895转自:http://paskaa.iteye.com/blog ... -
【HTML】模拟事件触发
2013-02-19 11:20 996使用JQuery很容易办到。 $("#myS ... -
js+css 简单的高亮选中对象
2012-08-23 16:14 1757功能: 点击列表中的对象时,为选中对象加上边框(高亮显示)。 ... -
document.execCommand()用法说明
2012-08-15 11:37 1981以下内容来自互联网: ... -
控制highCharts中坐标轴的起始刻度
2012-07-19 17:37 19707HighCharts的设定挺多的,用到了哪个就记下来,这次是关 ... -
控制Highcharts中x轴和y轴坐标值的密度
2012-05-30 15:36 29230绘制小一点的Highcharts图表的时候,因为图表太小了,坐 ... -
js中按字节截取字符串
2012-05-11 17:09 4943功能:在网页中显示过长的字符串,截取指定长度,结尾添加省略号。 ... -
用正则表达式分离脚本和其他内容
2012-04-06 18:20 1129//用正则表达式分离脚本和其他内容 function ... -
S.O.L.I.D五大原则之SRP(单一职责)
2012-03-20 16:06 1580文章转自:http://tech.ddvip.com 单一职 ...
相关推荐
开闭原则(Open/Closed Principle,简称OCP)是面向对象设计中的一个核心原则,它在S.O.L.I.D(Single Responsibility, Open-Closed, Liskov Substitution, Interface Segregation, Dependency Inversion)五大设计...
7.S.O.L.I.D五大原则之开闭原则OCP 8.S.O.L.I.D五大原则之里氏替换原则LSP 9.根本没有“JSON对象”这回事! 10.JavaScript核心(晋级高手必读篇) 11.执行上下文(Execution Contexts) 12.变量对象(Variable ...
前言 Bob大叔提出并发扬了S.O.L.I.D五大原则,用来更好地进行面向对象编程,五大原则分别是: The Single Responsibility Principle(单一职责SRP) The Open/Closed Principle(开闭原则OCP) The Liskov ...
【标题】"Desafio-04-S.O.L.I.D" 指向的是一个编程挑战,该挑战可能关注于SOLID原则的应用。SOLID是面向对象设计中的五个基本原则的首字母缩写,它们分别是单一职责原则(Single Responsibility Principle, SRP)、...
深入理解JavaScript系列(7):S.O.L.I.D五大原则之开闭原则OCP 深入理解JavaScript系列(8):S.O.L.I.D五大原则之里氏替换原则LSP 深入理解JavaScript系列(9):根本没有“JSON对象”这回事! 深入理解...
O - 开闭原则(Open/Closed Principle, OCP) L - 里氏替换原则(Liskov Substitution Principle, LSP) I - 接口隔离原则(Interface Segregation Principle, ISP) D - 依赖倒置原则(Dependency Inversion ...
深入理解JavaScript系列(7):S O L I D五大原则之开闭原则OCP 深入理解JavaScript系列(8):S O L I D五大原则之里氏替换原则LSP 深入理解JavaScript系列(9):根本没有“JSON对象”这回事 深入理解...
6. **S.O.L.I.D五大原则**: - 单一职责原则(Single Responsibility Principle, SRP):每个类只有一个职责。 - 开闭原则(Open/Closed Principle, OCP):类应该对扩展开放,对修改关闭。 - 里氏替换原则...