锁定老帖子 主题:如何应对表结构经常变化?
精华帖 (0) :: 良好帖 (4) :: 新手帖 (0) :: 隐藏帖 (2)
|
|
---|---|
作者 | 正文 |
发表时间:2009-12-25
作为架构师或者开发人员,面对业务方提出的数据结构变化的需求总是很头痛的,今天让你加个描述字段,明天让你再加个什么标记,后天又需要增加一个时间戳,千奇百怪,层出不穷,实在头痛。但是,我们不能随意的指责什么,因为业务在发展,而且我们不能也不应该因为技术或者实现的原因去否决一些业务变化,毕竟技术是什么?真正产生价值的还是业务!
那,在实践中,我们如何面对这种无法避免而且往往很难预期的数据结构变化呢?
第一种方法,预留字段 既然很难加字段,就预先留好一些备用,比如加上10个Date,20个VARCHAR,10个Number之类的,虽然看起来猥琐了点,而且没那么灵活,其实还是很实用的,生产中也有不少人使用,不过因为预先留的字段一般是没什么含义的,需要有额外的信息来描述他,COL1是什么含义,COL2是什么含义,演变到后来有的就干脆更极端,所有字段都是无意义的名字,全靠外部的meta信息来描述,这种用法据我所知至少有三个地方在使用,两个是我亲自听到设计者描述的,另一个是别人告诉我的
不管怎样,预留字段的方式还是很解决很多问题的,而且基本不影响性能,除了额外的meta信息描述外,也没有其他的负担。
第二种方法,使用复杂字段 这个应用的场景不是很多,在某些特殊要求下还是很有用的,比如,某个业务实体(某张表),有一些标记位,都是true/false之类的标记,可以理解为这个实体的一些属性,经常需要添加,这种情况,在生产中我们使用过用一个数字,按位来表示这些标记的,比如第三位表示他是不是付费用户,第四位表示他是合作方来的用户还是自己注册的,等等。还有一种情况,需要更复杂的属性列表,属性个数经常变,可以考虑使用一个文本字段,保存结构化的数据,比如自己定义一个xml的格式
使用复杂字段的好处就在于比较灵活,同一类型的数据可以放在一起(实际上相当于把应该是一个关联表的数据放一个字段里了),操作的性能也不错,但是复杂字段里面的内容查询比较困难
还有一种方法,将数据的存储和索引(需要查询的内容)分开存放,相当于主表就一个key-value,value就是一个大的xml(或者其他的一坨),把需要查询的字段放到其他单独的表里去,可以参考friendfeed如何使用mysql,这是一个实际的例子。实际上在02-03年的时候,老是面对这样的问题,我就在考虑这样的方案,我当初的想法是,用bdb来存储数据(就是那个key-value)了,要检索的数据放到lucene里去,但是因为那个系统对实时性的要求而没法实施,但是并不是每个系统都要求这么实时的,在有些地方还是可以考虑使用的
另外,还有column based db,也可以很好的解决这个问题,实际上他就本本回避了加字段的问题,不过现在似乎没有性能很好的实现
上面这些方案的,都有局限性,选用的时候要看场景的,而且有可能今天作出的决定是对的,过了两年就变的不适合了,事情总是在变化的嘛... 声明:ITeye文章版权属于作者,受法律保护。没有作者书面许可不得转载。
推荐链接
|
|
返回顶楼 | |
发表时间:2009-12-25
正在弄oracle的 xml db 不知道能否搞定,从目前的情况来看 字段变了,从前(界面)到后(逻辑),全变,谁让你不是做产品的,做解决方案只能怪自己命不好 老老实实改吧,逃不掉的!!
|
|
返回顶楼 | |
发表时间:2009-12-25
friendfeed用mysql实现key-value存储主要是解决在线ddl锁表影响ha的问题
|
|
返回顶楼 | |
发表时间:2009-12-25
好的设计不会出现表结构经常变化的问题,LZ反省下吧(只大致浏览了下内容,没仔细看)
|
|
返回顶楼 | |
发表时间:2009-12-26
x03570227 写道 好的设计不会出现表结构经常变化的问题,LZ反省下吧(只大致浏览了下内容,没仔细看)
任何“好的设计”都是短暂的,因为业务总在变化,否则的话,我们现在还写什么程序呢,用以前好的设计就可以了啊,这是极端了 现实中是,如果你的系统支持的是一个不太稳定的业务,那就必然会面临这个问题的 |
|
返回顶楼 | |
发表时间:2009-12-29
agan??
我的看法是..数据库设计不为了“未来”而设计,所以我反对“预留字段”的方法; 依我个人的经验上讲,表结构做到3范式,并且任何字段都不带结构(只是一个意义单一的值而已),总体来说这样的数据库设计是很好扩展的; “很好扩展”基本上是指如果业务要新增概念,那么只需要通过添加字段或者添加新表完成扩展,而不是更改字段本身或者删除字段(有点“开闭原则”的意思,我觉得不管是对象设计还是数据库设计这点是部分共通的) 看得出来你已经对这些“很好扩展”的扩展进行抱怨了; 确实,如果业务变化很快,那么就算变化朝着正常方向发展(只增不删改),也不免会让人觉得烦; 我觉得这种烦恼很大部分是因为我们不仅在代码中维护了所有的业务概念,同时在关系型数据库表中也维护了一份业务概念——我们要具体到某个字段来存储,表结构实际上非常具体地展现了业务数据——这就导致业务一变,除了代码要变之外,数据库表结构也可能变; 这样我觉得有意思的事情就来了:你需要用数据库进行关系运算么? 数据库表非常具体地展现了所有的业务字段细节,为的是做关系运算,比如连接查询; 简单看了一下你提到的“复杂字段”和后面的“key-value”方案,如果这样的方案能满足你的业务需要,那么说明你的业务是不需要数据库做关系运算的,进而也不需要关系型数据库了...所以这里你不妨考虑一下对象数据库 就像bigTable一样,所有的东西都有一个identity取出来,以一个对象的形式,所有的业务逻辑就只存在于代码中 |
|
返回顶楼 | |
发表时间:2009-12-29
最后修改:2009-12-29
要么能够多收钱 也就认了。 要么去死吧。
设计业务流程规范用户操作。计算机模型就是 输入 处理 输出。至于持久化的实现是很技术的问题,和业务没有关系。 至于“表结构经常变化” 要么是业务没搞清楚,要么就是方向错误。 |
|
返回顶楼 | |
发表时间:2009-12-29
现在的数据库应该都支持正则表达式查询吧
|
|
返回顶楼 | |
发表时间:2009-12-29
最后修改:2009-12-29
基于元数据的配置技术 方便修改 升级。 建议看看compiere的思想
|
|
返回顶楼 | |
发表时间:2009-12-30
如果需求变换,需要扩充功能,再好的设计也无法阻止表结构的变化,除非你能让客户不提这个需求或设计表时就能知道客户未来可能需要的全部功能,我上家公司的做法就是预留类型为varchar的备用字段,这个确实能应付一段时间的变化。不过我也在思索有什么更好的方法去应对时时变更的需求。
|
|
返回顶楼 | |