`
1000copy
  • 浏览: 74397 次
  • 性别: Icon_minigender_1
  • 来自: 成都
文章分类
社区版块
存档分类
最新评论

best practice 封装存储过程(续4)——越抽象,就越容易封装变化。

阅读更多


 

上回书 Tony  says

看起来它似乎并没有改善不同层次代码的耦合关系,以前例看,所有的针对数据库的调用都是通过C#层的RunProc实现的,似乎它本身就充当了隔离层的作用,为什么还要增加一个无用的层delete_dept(1)呢? 

 

你的问题提的很好。我会更加细致的解答你的疑问。

 

简单说,delete_dept语义上比RunProc更加抽象,没有那么多的细节,因此更加容易封装变化。

 

首先,我们从使用者角度考虑,本地函数或者Runproc方法的时候,那一个更加简单。

 

是的,函数也是有客户的,函数的客户就是它的调用者。我们看一个函数设计的好不好,关键要看对客户的代码是否隐藏不必了解的细节。

还是以代码为例来看,  当客户代码,比如button_click()内调用 

  RunProc("delete_dept",1)我们看RunProc需要用户了解那些信息:

 

1.          这是一个调用存储过程的方法

2.          这个存储过程名称是delete_dept

3.          这是部门的编号是1

而使用代码delete_dept(1)客户并不需要知道在RunProc内需要了解的信息12。当然3还是需要了解的。

我们再细致些,对比下两者的语义:

 

 

语义

delete_dept(1)

我要删除一个id=1的部门。

  RunProc("delete_dept",1)

(当前数据库连接下),调用一个叫做delete_dept存储过程,参数为1

 

我们每个人都做过客户,比如说做过装修的主人家,都知道和装修公司说,“恩,不要给我说那么多的细节,我就关心是否达到了我想要的效果”。对吗?

体验以下两者的语义,使用delete_dept(1),和使用RunProc("delete_dept",1)相比,哪一个让你这个客户更加轻松?

 

因此,用语义分析上看,delete_dept(1)只是说做什么,RunProc则是说如何做。这就是层次上的差别了。

 

其次,我们看看两者如何封装变化。要知道,软件的的最大问题在于适应变化。一个客户需求的变化,最理想的情况下,我们希望在一个地方解决,而不是到处修改。

那么,删除一个部门会有什么的变化呢?我经过整理,找到大家提到了的几个可能的变化

1.          存储过程命名不合适,需要修改

2.          需要考虑更多的错误处理

3.          需要用户给出更多的参数,比如 让用户自己输入部门的名称,加以验证。

 

为了便于分析,我们假设整个程序有3个地方需要调用删除部门。伪代码如下:

 

Button1_click()

{

     delete_dept(1) 

}

Button2_click()

{

     delete_dept(1) 

}

 

Button3_click()

{

     delete_dept(1) 

}

 

delete_dept(id)

{

   RunProc('delete_proc',id);

}

限于篇幅,我们只能举出这样的小例子:请稍微想象以下,这些调用(如button-click 可能分布在很多单元内。

 

我们来对比下两种情况下需求的变动,会导致多少个函数需要更新:

 

 

 

修改点

修改点

情况

localfunction

Runproc

1

1

3

2

1

3

3

5

4

 

看到这个数字,你并不觉得怎么样。可是当你把3换成100的时候,也许就不这么想了。

 

 

修改点

修改点

情况

localfunction

Runproc

1

1

100

2

1

100

3

102

101

合计

103

301

 

就是说,3个变化同时发生的情况下,前者需要修改103个函数,后者是301次。如果仅仅头两个发生的话,那么前者2次,后者200次——这就是差别——当调用增加的时候,我们考虑问题必须进入新的视角:在比较少调用的情况下,代码差点没有关系;当调用很多的时候,我们必须锱铢必较

 

100个调用是不算什么了。我们的checkError方法,我统计是1900多次调用,检查权限是990多次调用,更不要说更加基本的函数了。

 

前两情况,体现了我们一直以来 的一个最高理想——客户的一个需求变化,只要在一个地方就可以修改完毕。其中这样的变化仅仅看名称就看得出来。使用delete_dept(1),比RunProc需要了解的细节更好,因此,当细节变化发生的时候,前者更加容易封装变化。

 

可是,有人一定会说,第三种情况修改的点还是很多啊。你的封装不管用啊?

首先,不管有多少引用,两者的修改点都仅仅差一个,因此可以认为等同。其次,封装仅仅可以封住我们考虑到的情况,而不是所有情况。这种情况下,整个函数因为加入了参数,语义都已经发生了变化,是不是叫做delete_dept都不一定了,此时还要封装,就勉为其难了。再好的封装都不能解决所有问题,我们要做的是,尽可能的封装变化,而不是封装全部变化——这是永远也不可能的。

0
1
分享到:
评论
2 楼 1000copy 2010-06-10  
看来您用oracle比较多?下面我会发一篇文章,和oracle有关。发了你来看,欢迎指正。
1 楼 fansfirst2008 2010-06-10  
用了很长时间PLSQL,但是没有想这么多!
受教了,楼主强人!

相关推荐

    What is SAP Best Practice

    【标题】:“SAP Best Practice 概览” 【描述】:SAP Best Practice 是SAP公司提供的一套全面的方法论和预配置的解决方案,旨在帮助企业在实施SAP系统时能够快速、有效地达到业务最佳状态。它集合了SAP多年的行业...

    Unity插件——Best HTTP

    Unity插件——Best HTTP 封装好的网络插件,节省自己写http的时间

    sap best practice(应付帐款会计)

    SAP Best Practice(应付帐款会计)是一套预先配置的解决方案,旨在帮助企业高效地管理其应付账款流程。这一系列文档涵盖了从发票处理到付款的所有关键步骤,确保符合最佳实践和标准操作流程。以下是各文档的主要...

    How to get SAP Best Practice

    4. **工具支持**:标签提到的“工具”可能指的是用于导入、定制和管理SAP Best Practices的工具,如SAP Best Practices Explorer。这个工具可以帮助用户浏览、选择和下载适合他们特定需求的最佳实践内容。 5. **...

    Best Practice: Scale-Resolving Simulations in ANSYS CFD.pdf

    这些流动通常涉及强烈的非线性相互作用和快速时间变化。理解和模拟这类流动的关键在于正确选择流动物理模型、网格技术和数值设置。 4.1.1. 流动物理 理解流动的物理机制对于选择合适的模型至关重要,例如是否包含...

    Smalltalk Best Practice Patterns

    整本书不仅仅是关于代码的写法,还包括了软件开发过程中各个阶段对模式的应用,这对于程序员、项目经理、教师和学生都是极其宝贵的资源。 这本书可以帮助读者理解Smalltalk中的模式,并通过这些模式来提升代码质量...

    Android Design Patterns and Best Practice

    本资源包“Android Design Patterns and Best Practice”包含了多种格式的书籍(PDF、EPUB、MOBI)以及可能的源代码示例,旨在帮助开发者深入理解Android平台上的设计原则与实践。 首先,我们要了解设计模式的重要...

    Smalltalk Best Practice Patterns(Kent Beck).pdf

    - **Creation Parameter Method**:创建参数方法用于封装对象创建时所需参数的逻辑,简化外部调用者的工作。 - **Converter Method**:转换方法用于将数据从一种格式转换为另一种格式,如字符串到日期等。 - **...

    SSIS Best Practice

    4. **错误处理和日志记录**:有效的错误处理和详细日志记录对于调试和问题排查至关重要。设置适当的错误处理机制,如错误流和日志组件,以便快速定位和解决问题。 5. **使用缓存和缓冲池**:利用SSIS的缓冲池功能,...

    best practice for convolution neural network

    因此,本文作者——来自微软研究院的Patrice Y. Simard、Dave Steinkraus和John C. Platt,提出了一系列具体的最佳实践建议,以帮助视觉文档分析领域的研究人员利用CNN获得良好的结果。 #### 二、扩大训练集的重要...

    MGR Best Practice - 娄帅 - 20210522.pdf

    MGR与传统的异步复制机制相比,最大的特点是采用了多数派节点接收事务消息的PAXOS算法,并且可以自动处理故障切换、集群成员变化和选主等问题。 在MGR的架构中,有四个关键组件:Capture、Applier、Recovery和...

    Best Practice Guide Migration of SAP ABAP to SAP HANA

    4. **迁移过程中的考虑因素**: 迁移过程包括导出、传输和导入三个主要步骤。 - **导出**:需要从源系统导出数据和配置。导出工具和过程的正确使用至关重要。 - **传输**:导出文件需要被安全地传输到目标SAP ...

    UiPath Automation Best Practice Guide

    UiPath机器人开发的相关教程。This document outlines the standards and best practices to be considered by RPA developers when building automation processes with UiPath

    Oracle PL/SQL best practice

    4. 高性能PL/SQL: - 使用游标FOR循环代替显式循环,以减少数据库访问并提高性能。 - 利用绑定变量,防止SQL注入,同时提高查询执行计划的复用性。 - 适当使用嵌套事务和保存点,以控制回滚范围,提高事务处理...

    SQL Server DBA best practice

    ### SQL Server DBA 最佳实践解析 #### 关于文档 本文档主要介绍的是由EMC公司发布的关于SQL Server ...此外,随着技术的发展,某些细节可能会有所变化,因此在实际应用中还需结合最新的技术和产品文档进行综合考量。

    Best Practice--排序段的使用

    4. 优化查询结构,减少不必要的排序,例如在上述案例中,删除了不必要的`ORDER BY`。 5. 定期清理临时表空间,释放不再使用的空间。 通过监控工具,如`TOP SQL`,定期检查并分析`disk_reads`和`sots`,可以帮助识别...

    Xcelsius2008 Best Practice

    在《Xcelsius2008 Best Practice》一书中,作者首先介绍了Xcelsius2008的起源——作为一种“杀手级应用”,它最初是为了弥补传统电子表格(如Microsoft Excel)在展示数据方面的一些不足而诞生的。传统的电子表格...

Global site tag (gtag.js) - Google Analytics