一星期8天

Eight Days a Week - by The Beatles & 小陆

剔除设计中多余的概念

软件设计首先要整理用户的业务模型,然后以此为参照,结合环境条件,建立软件系统模型。在这个过程中,很重要的一点是:要剔除软件模型中多余的概念。

哪些是“多余的概念”呢?如果一个概念是从用户的业务模型中无法直接观察到的,而是设计者推想出来的,那么这个概念就是多余的概念。

我们想象一个铁路公司,经营着ABCD四个城市之间的路线。这几个城市的位置如下:



铁路公司的老板想做一个售票系统,他找到一家软件公司。假设我就在这个软件公司工作,担任这个项目的负责人。铁路公司的老板这么对我说:从A到B的票价是50元,从B到C的票价是60元,从C到D的票价是30元,如下:



在这个基础上,两个城市之间的票价是各段之和。比如:从A到C的票价是AB+BC,就是110元。

于是,回到办公室里,我开始设计这个系统。我想:这个系统很简单,以A城市作为起点,把从A城市到各个城市之间的票价记录下来。就像这样,我设计了一个数据表,保存票价,他是这样的:

SQL>SELECT * FROM TICKET_PRICE;

CITY    PRICE
---------------
A       0
B       50
C       110
D       140

当旅客来买票,要从B到C去的时候,我们就用C的票价减去B的票价,得到从B到C的票价,得到60元。想从D到B,就用D的票价减去B的票价,得到90元。

这个设计非常简洁,看上去没什么问题。按照这样的想法,我们开始写代码了。但是,很快我就遇到了麻烦。

铁路公司的老板打来一个电话,他说:我们正在对票价做一些调整,从A到B的票价保持50元,B到C保持60元,但是从A直接到C的票价现在调整到100元。并且从C到A的票价要打一个8折,就是80元。

现在麻烦了,TICKET_PRICE这个表面临着重大的变动,所有基于这个表的业务逻辑都要改了。

烦恼的由来是什么呢?原因在于,这个设计是基于我的一个推论,而不是可以直接观察到的业务事实。直接观察到的业务事实是:A到B的票价是50元,B到C的票价是60元,A到C的票价是110元……而我在这个基础上做了一个推断:A到C的票价是AB+BC。当然,我做出这个错误的推断,有铁路公司老板的一部分“功劳”。无论怎样,变更不可避免,铁路公司和我,都必须承担这个错误的后果。铁路公司要追加项目投资,我们的开发成本要上升,而我自己,肯定要加班了。

这个设计中有一个多余的概念:A城市是一个基准点。这是一个在业务过程中无法直接观察到的概念,而我错误的将他作为整个系统的基础,让所有城市之间的票价以他们到A城市的票价为基准。

从业务中能够直接观察到的是什么呢?只有两个城市之间的票价。一个乘客来到铁路公司买票,从A到B是50元,从B到D是90元……他能观察到的只有这些,而没有作为某个基准点的A城市。系统的设计应该基于坚实的业务基础,而不是任何推断。“基准”这个概念需要从设计中剔除掉。

重新设计这个系统,应该用下面这样的形式描述城市之间的票价:

A B C D
A 0 50 110 140
B 50 0 60 90
C 110 60 0 30
D 140 90 30 0

当然,我可以用这样的数据表来保存这样的票价:

SQL>SELECT * FROM TICKET_PRICE;

START     DESTINATION      PRICE
---------------------------------
A         B                50
B         A                50
A         C                110
C         A                110
B         C                60
......

如果我一开始就这样设计的话,接到铁路公司的电话后,心里就会舒服多了。

posted on 2006-04-24 01:58 小陆 阅读(1462) 评论(17)  编辑 收藏 所属分类: 软件工程实践

评论

#1楼  2006-04-24 08:35 马志远      

我总是隐约感觉你的这个设计不是很好.   回复  引用  查看    

#2楼  2006-04-24 08:38 马志远      

我觉得那样子设计数据库, 是属于"比较笨"的方法, 把所有城市的加减数值都事先写好,存储到数据库中的. 然后是死的, 从数据库中读出来而已.

如果让你设计一个全国性的铁路网站, 你的设计方式, 感觉就很不爽了.

  回复  引用  查看    

#3楼  2006-04-24 08:40 马志远      

假设你在A城市,比如"北京", 现在"上海"的到那儿去,你就得自己填写上1*2=2条数据.

现在又有一个"厦门"城市,你就得写上2*2=4条数据.

再加一个城市"重庆",你就得写上2的3次方条数据.

我不敢想象,全国铁路让你这样子设计, 会是怎么样的效果.   回复  引用  查看    

#4楼  2006-04-24 08:45 Icebird      

在分析需求, 整理设计的过程中, 一定需要考虑需求变更的部分, 很显然, 一个售票系统的票价一定是可变的, 并且票价的高低与两地间的距离不一定成正比, 票价随时可能根据市场变化而作出调整, 基于以上的考虑, 恐怕不会有人会自作聪明的作出如文章所描述的推论

因此我以为多余的概念在某种程度上就意味着错误的概念

在设计的过程中, 一定需要多加考虑系统如何能够满足以后可能发生的需求变更   回复  引用  查看    

#5楼  2006-04-24 08:45 Dflying Chen      

还有一点你没有考虑到,就在你举的例子基础上,比如AD之间加了一条新路线,那么从A
到D就有两个方法了,你的业务逻辑又要改了,呵呵。
铁路本身是一个图的概念,这样的表示方法给我的感觉是您没有图的概念。   回复  引用  查看    

#6楼  2006-04-24 08:50 音乐虫子      

老兄,你整个设计思路就不对,这样的表结构以后还会遇到非常大的麻烦   回复  引用  查看    

#7楼  2006-04-24 09:14 沐枫      

楼主只是举个范例而已。真正的铁路系统肯定没这么简单。
所以就此例说铁路售票系统是不该的。

就主题来说,最重要的问题是:需求分析不当
  对于一个软件,不仅仅是了解对方提出来的需求,而是先要了解该行业的普遍需求。
  显然铁路售票现存的状况肯定不是最初假设的那么简单。因此,后面需求的变更是合理的--因为要求做是的铁路售票系统,而售票系统本来就可以调整各段的价格,以及各种打折、优惠的可能性,还包括不同车种不同车厢、座位的不同价格浮动。
  回复  引用  查看    

#8楼  2006-04-24 11:10 老燕      

@沐枫:准确地归纳了文章的中心思想
  回复  引用  查看    

#9楼  2006-04-24 13:51 Konimeter      

需求分析一定要细致和长远。。。   回复  引用  查看    

#10楼 [楼主] 2006-04-24 15:25 小陆      

假设有n个城市,任意两个城市之间都可以买直达的车票,那么这个系统的车票数量是n*(n-1)个。实际上,不会在任意城市之间都有直达的车票,铁路公司自然会在重要城市之间形成主要线路,以此为基础形成一些支线。

第二种设计其实是很符合“图”的概念的。

在如今这样市场竞争强烈的环境里,第一种设计肯定是很少有人采用了。但是如果在10年前,情况可不一定。即使是在现在,考虑一下上海市的地铁售票系统,肯定会有人按照里程来计算票价吧。   回复  引用  查看    

#11楼  2006-04-24 16:17 双鱼座      

软件行业好象有一个惯例:自己的设计错误总是让用户来埋单。这可能也体现了这个行业的一种浮燥吧。我想起了Steve McConnell讲的那个故事:一个建筑师给客户盖了套房,其中没有电气部分,原因是客户没有提供电气方面的要求...   回复  引用  查看    

#12楼  2006-04-24 22:56 敲门 [未注册用户]

回复真是.....
无语。

说故事的一种技巧而已。
为了说明问题,我们往往简化周围环境,突出我们想表达的重点,这个项目负责人早期的愚蠢的思考行为是我们要避免的,这是这个故事的重点。

试试看,在你的项目组中,要说清楚一个问题的时候,简化周边条件,是非常又效果的,当然这也是一种能力。

诚然,这个系统让100个人设计,肯定会得到100个不同方案,然而变化产生之后,成本的变化会更大。
作为读故事的人,觉得主角如此愚蠢,是因为还没有实质的感觉到需求的复杂。
看看这篇文章,http://koman.blogchina.com/1744581.html

其实项目做的越多,越心虚,越害怕。   回复  引用    

#13楼  2006-04-25 08:49 naive_1010 [未注册用户]

不错的一个启发!!

有点像在讲解一个数学命题!!   回复  引用    

#14楼  2006-04-25 09:57 sp1234 [未注册用户]

你没有说明为什么“基准”被作为基准,也就是它是根据什么经验被作为基准的。

更没有说明“基准应该从这个设计中剔除”。

你的文章含糊了中心思想,就好像是说“设计肯定碰到矛盾,因此干脆不要有概念”,意义不大。

批判时总是很有道理,但是看不出大张旗鼓明确应该做出的“临时”设计思路是什么,意义不大。   回复  引用    

#15楼  2006-04-25 09:59 sp1234 [未注册用户]

最有意义的启发,是明确说明什么样的基准是对的。而不是仅仅说明什么基准是错的。   回复  引用    

#16楼  2006-04-26 21:51 0776 [未注册用户]

真是越弄越复杂了   回复  引用    

#17楼  2006-06-23 09:36 Sweeper      

回复马志远:
1、全国有火车站的城市也就K级(包括县级)。
2、一次火车路过的城市也就不超过50个。
3、本人7年前设计的列车时刻表就是如楼主后来的方法,把铁道路的全部车次都录入进去了,也不到10万条记录。有什么不可想象?
  回复  引用  查看    


标题  
姓名  
主页
Email (只有博主才能看到) 
验证码 *  看不清,换一张 [登录][注册]
内容(请不要发表任何与政治相关的内容)  
  登录  使用高级评论  新用户注册  返回页首  恢复上次提交      
 
另存  打印