最近一直在一个培训公司做着极为无聊的培训,所以一直都没有时间上网。今天突然发现这里可以上无线,嘿嘿,就上来继续把这个文章完成。

上次说到了设计原则中的单一职责原则,今天时间比较紧,我就继续往下写,也不知道能写几个。

现在来说一下设计模式的核心,开放封闭原则(OCP原则)。开放封闭原则我想每一个人都可以从字面上很容易地理解他的意思,就是说对扩展开放,对修改封闭。一个优秀的软件是可以无限扩展的,而且是不需要修改类的内部结构的(当然这是指的理想状况,实际上,无论设计多么优异的软件,一旦扩展,总是要对类内部进行修改的)。

上次我记得我说过,设计模式,也是OO的目标,无非是两个,可重用和可扩展。我们来从这两个方面来分析OCP,我们先说可扩展,这个我想我不用多说了,都说过对扩展开放的,当然是可扩展了。可重用等我先举个例子再来分析下这个。

在这个,我举个我前两天做的一个小型计算器。我们先来分析一下这个小型计算器,我把一个小型计算器的按钮抽象为以下几个功能:数字键,二元运算符,一元运算符,修饰符(比如说小数点),等于号。然后我把这几个功能分别封装成一个自定义控件。现在来说下二元运算符,代码如下:

Code
 1    public partial class ButtonOperateTwo : UserControl
 2    {
 3        private TextBox textBoxResult = null;
 4        public ButtonOperateTwo()
 5        {
 6            InitializeComponent();
 7        }
 8        public ButtonOperateTwo(string text, TextBox textBoxResult)
 9        {
10            InitializeComponent();
11            this.buttonOperate.Text = text;
12            this.textBoxResult = textBoxResult;
13        }
14
15        private void buttonOperate_Click(object sender, EventArgs e)
16        {
17            SaveNumber1(this.textBoxResult.Text);
18            this.textBoxResult.Text = "0";
19            SaveOperate(this.buttonOperate.Text);
20        }
21
22        private void SaveNumber1(string num1)
23        {
24            Number.Number1 = this.textBoxResult.Text;
25        }
26        private void SaveOperate(string operate)
27        {
28            Number.Operate = operate;
29        }
30    }
Code
1    public struct Number
2    {
3        public static string Number1 = "0";
4        public static string Number2 = "0";
5        public static string Operate = "+";
6    }

在这里,我来简单地说下我这段程序的思路。我之前没有做过任何Winform程序,没有找到缓存,因此我声明了一个结构体来存储所需要的数字和操作符。然后当点击二元运算符后,我就把textBoxResult的Text传入到Number1中,然后同时也把操作符来暂存到结构体中。这样,以后无论有什么二元运算符,我们都不需要再写那么多重复的代码,而只需要简单的调用这个二元运算符就可以了,而不需要任何修改。

因此,我们很常用的自定义控件,就是开放封闭原则的最好体现。

基本上所有设计模式的目的都是开放封闭。在这里,我来简单地提下一个很好地体现了开放封闭的设计模式——工厂模式。

工厂模式是创建者模式的一种,用于解决对象的创建问题。我的这个计算器应用的就是工厂模式。

我这里不大方便画图,就用语言来描述一下吧。

我创建两个类库,分别为运算类库和工厂类库。在运算类库中有一个基类OperateBase,在他的下面有两个子类分别为一元运算子类和二元运算子类。而这个子类下又分别有着具体的运算子类。在工厂类库中有两个基类,分别是二元运算工厂类和一元运算工厂类。而每个基类下又有着具体的运算工厂类,分别用于返回运算类。我们来简单地看一些示例代码:

Code
 1    public abstract class OperateBase //运算基类
 2    {
 3        public abstract string GetResult();
 4    }
 5    public abstract class OperateOne:OperateBase   //一元运算基类
 6    {
 7        public double Number1
 8        {
 9            get;
10            set;
11        }
12    }
13    public class OperateSqrt:OperateOne   //开方运算
14    {
15        public override string GetResult()
16        {
17            double result;
18            result = Math.Sqrt(Number1);
19            return result.ToString();
20        }
21    }
22    public abstract class OperateFatoryOne //一元运算工厂基类
23    {
24        protected OperateOne thisOperate = null;
25        public abstract OperateOne GetOperate();
26    }
27    public class OperateFactorySqrt : OperateFatoryOne  //开方运算工厂类
28    {
29        public override OperateOne GetOperate()
30        {
31            return new OperateSqrt();
32        }
33    }
34    private string ReturnResult()  //客户端调用方法
35        {
36            try
37            {
38                OperateFactory.OperateFatoryOne thisOperateFactory = null;
39                switch (this.button1.Text)
40                {
41                    case "+/-":
42                        thisOperateFactory = new OperateFactory.OperateFactoryReverse();
43                        break;
44                    case "sqrt":
45                        thisOperateFactory = new OperateFactory.OperateFactorySqrt();
46                        break;
47                    case "1/x":
48                        thisOperateFactory = new OperateFactory.OperateFactoryCountDown();
49                        break;
50                    case "%":
51                        thisOperateFactory = new OperateFactory.OperateFactoryPercent();
52                        break;
53                }
54                OperatingSystem.Operate.OperateOne thisOperate = thisOperateFactory.GetOperate();
55                thisOperate.Number1 = Convert.ToDouble(this.thisTextBox.Text);
56
57                string result = thisOperate.GetResult();
58                return result;
59            }
60            catch 
61            {
62                string result = "您的输入有误";
63                return result;
64            }
65                
66        }
67
68

于是,我们就可以自由地添加一元运算符了,当添加时,我们只需要添加一个运算子类,添加一个工厂子类,然后在客户端的switch的case中添加一个条件。当然,这里就是我说的,不存在完全的开放封闭,无论设计多么优异的软件。即使在这里用抽象工厂+反射,也仍然需要加以修改,我没那样设计的原因是因为那样的设计对效率实在有点.....

最后,对以上的文字做个总结。

开放封闭原则是整个设计模式的核心,依我的理解,所有的设计模式,包括所有的设计原则都是围绕着OCP展开的。一个优秀的软件设计师可以忘记所有的设计模式,甚至都可以忘记所有的设计原则,但是开放封闭原则必须永记心中。

好了,就写到这。然后说个昨天开《建筑的永恒之道》,上面有这样一句话,什么才能成就建筑的永恒之道,学会方法,然后忘掉他。

从设计原则谈软件开发(二)相关推荐

  1. java学习方法-浅谈软件开发的神速进步

    中国人大都喜欢用武侠小说来比较软件开发,但是在实战武功中,只有葵花宝典才是最厉害的,也只有掌握了葵花宝典,才能称为"不败". 1浅谈软件开发的神速进步 1.1什么才是软件开发的葵花 ...

  2. 浅谈软件开发工具CASE在软件项目开发中发挥的作用认识

    浅谈软件开发工具CASE在软件项目开发中发挥的作用认识 内容摘要:阐述了CASE工具作为 一种开发环境在软件项目开发中所起到的开发及管理作用.CASE工具实际上是把原先由手工完成的开发过程转变为以自动 ...

  3. 架构师实战培训(架构设计+数据后台+快速开发+二次开发+发布部署)

    架构师实战培训(架构设计+数据后台+快速开发+二次开发+发布部署)系列视频课程 课程目标 学习MIS系统.高并发系统.单机系统设计思路: 理解设计模式,学会命令模式: 适用人群 CIO.CTO.技术总 ...

  4. 从足球赛谈软件开发!!!!

    昨晚看切尔西的比赛的时候突然联想到了软件开发,呵呵,来看足球赛: 1.根据比赛双方的实力.主客场.天气等等各方面因素来比赛双方都会制定自己的目标,战平.胜或别的目标. 2.需要在有限的时间内(90分钟 ...

  5. api 二次 开发 禅道_浅谈-软件开发流程

    先直接放出我对软件开发的相关人员职责和流程: 图一:软件开发的相关人员职责 以下是截屏的开发流程泳道图: 横轴是相关开发人员的工作模块:纵轴是从上至下开发时序周期. 图二:软件开发的流程图 从职责图和 ...

  6. 浅谈软件开发架构模式

    本文作者将介绍他对于软件开发架构模式的一些思考和实践. 背景和问题 我个人平时会比较慎用"架构"这个词 一方面是觉得业界有很多架构大师和架构模式,而我的认知和实践有限: 另一方面是 ...

  7. 架构设计--仅是软件开发之第二大影响力?!

    SDWest2006(译注1)对我来说是个有趣的大会.我除了星期三之外(当时我正飞往费城参加一个客户会议 == 因此错过了Jolt颁奖部分)每天都在演讲.我也参加了一些谈话和会议:其中最引人关注的是M ...

  8. 浅谈软件开发项目的质量控制

    一.引言 J.M.Juran认为质量控制是一个常规的过程,通过它度量实际的质量性能并与标准比较,当出现差异时采取行动.由此,DonaldReifer 给出软件质量控制的定义:软件质量控制是一系列验证活 ...

  9. 【面试】 CVTE 视源股份 C++ 软件开发 二面

    微信搜索"编程笔记本",获取更多信息 ------------- codingbook2020 ------------- 今天继续分享 CVTE 视源股份的 C++ 软件开发的二 ...

最新文章

  1. tee 和 ree分别是什么意思?
  2. string stringbuffer stringbuilder 区别
  3. dbscan算法c语言实现,用C++实现DBSCAN聚类算法
  4. 高能干货:OpenCV看这篇就够了,9段代码详解图像变换基本操作
  5. Zookeeper基础简介
  6. dapper利用DynamicParameters构建动态参数查询
  7. webApi项目中的问题
  8. java实现续打功能_银行存折套打续打功能 -- 报表如何记录上次打印的位置
  9. ai怎么平均排列_一篇AI打麻将的论文,理科生眼中的麻将是这样的
  10. 网络安全基础——批处理编写
  11. java selenium 登录_java+selenium实例已打开chrome 实现自动化登录页面账号密码 | 茶杯猫...
  12. 材料成型过程计算机控制系统,材料成型及控制工程专业解读_材料成型及控制工程专业介绍_材料成型及控制工程专业开设课程-高考圈...
  13. 2017 Postgres大象会 TBase可靠性探究ppt
  14. HDMI转mipiCSI+Audio,东芝,TC358743,视频转换芯片
  15. 华为鸿蒙os3.0评测,华为鸿蒙OS威力初显!实测体验比EMUI更好 功耗却更低 惊喜还有很多...
  16. [Ahoi2014Jsoi2014]骑士游戏(SPFA)
  17. 手把手教你搭建入门级免费私有云盘NAS——基于syncthing——基础篇(树莓派、PC机)
  18. mima.php密码找回,蝉知系统忘记后台管理员密码怎么办?
  19. 基于Springboot开发实现的图书管理系统(附源码)
  20. 面试必备:聊聊sql优化的15个小技巧

热门文章

  1. mysql占用资源最小的语句_MySQL一个语句查出各种整形占用字节数及最大最小值的实例...
  2. 编写linux下跑马灯应用程序,01 arm11 led 跑马灯程序
  3. c++ string replace_JAVA应用程序开发之String类常用API
  4. MaxCompute 多行数据合并为一行数据
  5. python 使用安装虚拟环境 virtualenv
  6. 病毒的灵魂拷问(绝对原创)
  7. 微信小程序左滑删除效果的实现完整源码附效果图
  8. 1 OC 对象的本质(一个NSObject 对象占用的内存大小)
  9. 【仿去哪儿登录】UITextField输入时检查输入框是否为空
  10. 各种小的 dp (精)