+ h3 X7 }( G& l i 总共 24 个指南性技巧,涵盖表内字段设计以及应该避免的常见 , D* ]0 b! |6 M 问题等。 ) l% q, H5 X8 `0 j+ C 5 @0 e6 t% { H K5 e+ d! f 第 3 部分 - 选择键 + U# i" @/ \. @. t- Y0 e4 B0 y; @/ C2 Y9 ]; e- v
怎么选择键呢?这里有 10 个技巧专门涉及系统生成的主键的正 . N h% v8 l9 z: T/ w; W! L7 y 确用法,还有何时以及如何索引字段以获得最佳性能等。 2 k$ _" e3 h1 Y6 @8 b6 { / v( I! C- P! _ 第 4 部分 - 保证数据完整性3 F" ]4 y+ M% R/ ]4 [8 D
& Q$ {2 _% x' v3 A$ Q- f 讨论如何保持数据库的清晰和健壮,如何把有害数据降低到最小0 P1 E6 O) m7 l. M
程度。7 H* `' h4 }5 V4 l
+ x1 J* {) H( v
第 5 部分 - 各种小技巧+ k# B, A* o" D% k" Y' z- I& J
9 W# K, V0 l' r& w8 y) W
不包括在以上 4 个部分中的其他技巧,五花八门,有了它们希 9 G# p! }7 Z6 I9 n 望你的数据库开发工作会更轻松一些。 3 F- U C ]+ r% _0 @. \1 C9 k/ X. `1 r7 |, U N: k! M
% [) K6 c v" ]4 Y1 `
§ 第 1 部分 - 设计数据库之前 & U; E& ?0 ^" h n ──────────────7 G/ i/ E5 Z5 R6 D+ I
6 G1 E( i0 y; a$ n ■ 考察现有环境 6 H$ I) |" m2 O; g* a/ Q' C 0 a1 m4 A7 G, ?) z* A8 \3 Y( i9 y 在设计一个新数据库时,你不但应该仔细研究业务需求而且还要 9 @" }# A7 H" ~: T# b 考察现有的系统。大多数数据库项目都不是从头开始建立的;通常, / T- j6 B* L1 b( u! T 机构内总会存在用来满足特定需求的现有系统(可能没有实现自动计0 t. i7 d* }( k
算)。显然,现有系统并不完美,否则你就不必再建立新系统了。% t# j% w% S+ F# a L
/ \, w$ j; k. a! y8 n; z. A0 W# x1 r0 t: G
但是对旧系统的研究可以让你发现一些可能会忽略的细微问题。2 d( t6 K G4 e; d# }
一般来说,考察现有系统对你绝对有好处。 * p+ T; G2 ]" i1 x! i) g( w; y. v. ^+ C" N0 r9 f! R% q
■ 定义标准的对象命名规范7 x% z& w8 c0 h
; R4 \' P. g1 Y1 z' T6 x
一定要定义数据库对象的命名规范。对数据库表来说,从项目一 ( }' n8 z5 }8 p9 x 开始就要确定表名是采用复数还是单数形式。此外还要给表的别名定) K& ~- ^; H N# `
义简单规则(比方说,如果表名是一个单词,别名就取单词的前 4 , l; F4 o$ \4 m$ X l4 m3 ? 个字母;如果表名是两个单词,就各取两个单词的前两个字母组成 ! p& E2 T( s j: P4 L 4 个字母长的别名;如果表的名字由 3 个单词组成,你不妨从头两 - P0 r# b" ]6 A% q7 k' [: S 个单词中各取一个然后从最后一个单词中再取出两个字母,结果还是 & j$ H' M4 y/ l; C 组成 4 字母长的别名,其余依次类推)对工作用表来说,表名可以 / V; _- d4 i: q9 z 加上前缀 WORK_ 后面附上采用该表的应用程序的名字。表内的列[ / F+ Z' S0 J7 V* B9 i
字段]要针对键采用一整套设计规则。比如,如果键是数字类型,你 % B% V) n) N) R 可以用 _N 作为后缀; 5 h9 \! c: U/ y9 P5 t$ W' c $ }0 e, O, [: A( t v0 I3 r 如果是字符类型则可以采用 _C 后缀。对列[字段]名应该采用标3 y/ [/ a9 R( Z. v5 \7 T
准的前缀和后缀。再如,假如你的表里有好多“money”字段,你不 # [0 B4 e! r' N$ s. }) _( ~, e 妨给每个列[字段]增加一个 _M 后缀。还有,日期列[字段]最好以 ' I6 K. W- l( L! { D_ 作为名字打头。 6 J, T4 H! U. e& ]3 e c4 ?4 f 1 n N c/ V* J 检查表名、报表名和查询名之间的命名规范。你可能会很快就被 ! }: V; [" E. T0 D6 q. k. u 这些不同的数据库要素的名称搞糊涂了。假如你坚持统一地命名这些# S9 `4 w4 D. @7 l. L% L0 e
数据库的不同组成部分,至少你应该在这些对象名字的开头用 $ E( c. ]% m% d. \: m4 q! ~
Table、Query 或者 Report 等前缀加以区别。; f1 }/ i B% T, V7 ~- i2 }
; z$ X7 ?( K; H9 v! C
如果采用了 Microsoft Access,你可以用 qry、rpt、tbl 和 & h3 o: y) k6 }! g5 \; u mod 等符号来标识对象(比如 tbl_Employees)。我在和 SQL 2 z2 v! b' q$ a: F) A
Server 打交道的时候还用过 tbl 来索引表,但我用 sp_company % F- [/ d+ d$ j# B$ g S9 ~ (现在用 sp_feft_)标识存储过程,因为在有的时候如果我发现了& _! N* t$ e4 I! V ?$ r! h
更好的处理办法往往会保存好几个拷贝。我在实现 SQL Server & d+ P% W1 |, S) ~
2000 时用 udf_ (或者类似的标记)标识我编写的函数。 ) ?9 L; Q( N8 R& v. v, R 9 k4 D" N3 F+ E+ a5 ]5 h 工欲善其事, 必先利其器采用理想的数据库设计工具,比如: 2 \1 {4 m1 L. w4 h/ s3 f5 p! u SyBase 公司的 PowerDesign,她支持 PB、VB、Delp he 等语言,通 , P) e. f& ?: Q: k 过 ODBC 可以连接市面上流行的 30 多个数据库,包括 dBase、- ?9 m, w1 C% ^* M6 @# e! ?: ], ?$ i9 }
FoxPro、V FP、SQL Server 等,今后有机会我将着重介绍 2 p3 {! ~) ?$ T; ~4 U PowerDesign 的使用。 9 N. u2 N+ M) `1 L0 j6 G* j( z8 J/ [# K* p, d
■ 获取数据模式资源手册8 w$ ~; ]: Y, X: i" l+ ?( n
$ Y* B6 y; l* w4 l7 q
正在寻求示例模式的人可以阅读《数据模式资源手册》一书,该- z& C$ X* m# y! V% e5 x/ V
书由 Len Silverston、W . H. Inmon 和 Kent Graziano 编写,是 * y; @2 u0 k2 F$ j! j* i( B 一本值得拥有的最佳数据建模图书。该书包括的章节涵盖多种数据领 - d) h& V/ O. |' U! S) a" t 域,比如人员、机构和工作效能等。其他的你还可以参考:[1]萨师9 K5 V3 O$ P- R% P+ n
煊王珊著数据库系统概论(第二版)高等教育出版社 1991、[2][美] 4 J' f( T8 k# s( |# X% ~8 V3 C Steven M.Bobrowsk i 著 Oracle 7 与客户/服务器计算技术从入门 * L `% \7 C n1 r' H" ] 到精通刘建元等译电子工业出版社, 1996、[3]周中元信息系统建模 ' ?% N0 V! N( z% _% s 方法(下) 电子与信息化 1999年第3期,1999 畅想未来,但不可忘8 M z' v4 u! O9 h+ i3 @
了过去的教训我发现询问用户如何看待未来需求变化非常有用。这样 - e2 |* B3 I- e4 F 做可以达到两个目的:首先,你可以清楚地了解应用设计在哪个地方* ?& s9 {6 s* O* } Z
应该更具灵活性以及如何避免性能瓶颈;其次,你知道发生事先没有3 H- e( v2 i) Q% m
确定的需求变更时用户将和你一样感到吃惊。1 |. T0 K& t( H( A$ k" I7 ]
8 o3 \* K3 _: t5 F; y 一定要记住过去的经验教训!我们开发人员还应该通过分享自己 # P" b8 b( l( Y 的体会和经验互相帮助。 1 `0 c' Y( I; x1 r" E; B( i& M) g ! [# P; p4 z5 a9 S6 K9 Y- E- A8 Y' F 即使用户认为他们再也不需要什么支持了,我们也应该对他们进/ C; Q1 V2 n2 J- a/ g' }
行这方面的教育,我们都曾经面临过这样的时刻“当初要是这么做了, }( V- [! @# a( k% d
该多好..”。 8 ^; }) q6 H8 m' c, A # e3 |1 F4 d; I6 b ■ 在物理实践之前进行逻辑设计5 p$ {7 z/ i m" [# u4 \
4 e1 M$ Y3 J4 n1 f: p 在深入物理设计之前要先进行逻辑设计。随着大量的 CASE 工具 8 p, u3 B6 C! K9 |8 g) t# q/ R 不断涌现出来,你的设计也可以达到相当高的逻辑水准,你通常可以 + u- \/ b, q/ W/ e& v8 r 从整体上更好地了解数据库设计所需要的方方面面。 2 K$ Z' g S) l5 I: ?2 L9 o3 v % l# c7 N5 ?; [' T. H ■ 了解你的业务 ( ]. P" k b/ Q/ C" h& q1 [. n, O6 m$ Z: J- w
在你百分百地确定系统从客户角度满足其需求之前不要在你的 7 W, M* q$ l2 Y. H! a9 c% h ER(实体关系)模式中加入哪怕一个数据表(怎么,你还没有模式? Z! @1 N& g7 H- t1 U 那请你参看技巧 9)。了解你的企业业务可以在以后的开发阶段节约 $ I0 O( h; v, o7 z U' k* x: M 大量的时间。一旦你明确了业务需求,你就可以自己做出许多决策了。 / ?+ Z2 k: ]' I$ D, t7 D- V i% P7 v3 K. ?* H; O3 ] a% a
一旦你认为你已经明确了业务内容,你最好同客户进行一次系统 6 g5 V3 W- q' }- {" z- {1 S$ z 的交流。采用客户的术语并且向他们解释你所想到的和你所听到的。) B, i' ]6 C4 ^
同时还应该用可能、将会和必须等词汇表达出系统的关系基数。这样/ x: D- a1 k+ l4 k. x+ _
你就可以让你的客户纠正你自己的理解然后做好下一步的 ER 设计。# U1 m C' O* w2 y$ u. {4 t7 m
! K5 [ n* o1 o6 m, A) M ■ 创建数据字典和 ER 图表0 r8 V0 ^, G4 h" s3 m
0 k% {, F- e) b+ q 一定要花点时间创建 ER 图表和数据字典。其中至少应该包含每 3 ~1 d( r: }8 E: ~) P% A 个字段的数据类型和在每个表内的主外键。创建 ER 图表和数据字典& G3 V7 B4 K2 `( H& k6 N
确实有点费时但对其他开发人员要了解整个设计却是完全必要的。越 9 H# M4 V& F6 h& ^) M 早创建越能有助于避免今后面临的可能混乱,从而可以让任何了解数 ( a; G1 y0 r5 L5 @6 T: d 据库的人都明确如何从数据库中获得数据。 5 R0 Z$ j- t3 p& p) i1 g$ b' ]3 L1 ^4 L8 L4 N! k2 @) d3 S
有一份诸如 ER 图表等最新文档其重要性如何强调都不过分,这2 D. ?4 G, E- h+ y" X/ D! M
对表明表之间关系很有用,而数据字典则说明了每个字段的用途以及 # D- n1 Y3 w! d9 \- T& W 任何可能存在的别名。对 SQL 表达式的文档化来说这是完全必要的。 6 D8 i6 k6 ]; W" D% ~3 p( g 2 W! q+ L; d& R9 U' f( G& i ■ 创建模式 R. v# A0 `) g& ]/ z* w
1 K6 K2 r& o( j+ R# A& U$ c4 x
一张图表胜过千言万语:开发人员不仅要阅读和实现它,而且还 ! w( \: c2 C/ B& Z- J 要用它来帮助自己和用户对话。模式有助于提高协作效能,这样在先 / f, K- t: v$ y 期的数据库设计中几乎不可能出现大的问题。 7 q/ Q& m3 G6 `# L _/ y 5 U" j4 K! O% s, | 模式不必弄的很复杂;甚至可以简单到手写在一张纸上就可以了。 . _0 {0 C# @4 c! D/ ~, ^' I" R 只是要保证其上的逻辑关系今后能产生效益。 " p- J n5 q7 {9 [% j' X( p1 d& `5 _3 ?
■ 从输入输出下手/ O2 w) M1 j; x% R: i6 s
, w8 i# N8 V; h0 ?- { R! z 在定义数据库表和字段需求(输入)时,首先应检查现有的或者5 Q! Z3 O) A! X1 t
已经设计出的报表、查询和视图(输出)以决定为了支持这些输出哪9 h5 N6 @* Y& B+ f4 k1 {+ [: `. W
些是必要的表和字段。举个简单的例子:假如客户需要一个报表按照 " F1 y, v3 L3 R 邮政编码排序、分段和求和,你要保证其中包括了单独的邮政编码字, n/ J1 e9 E! n8 p& R
段而不要把邮政编码糅进地址字段里。7 `+ q" R4 G" \6 D& E6 _
8 W' X) S7 V4 M6 G
■ 报表技巧 F/ v4 }3 y; ]! X K6 ?' ~( k& O ~: F6 j8 {5 s# _ 要了解用户通常是如何报告数据的:批处理还是在线提交报表?6 V* }1 W% K3 a9 ^0 h M
时间间隔是每天、每周、每月、每个季度还是每年?如果需要的话还; n# S8 @) n; S. r
可以考虑创建总结表。系统生成的主键在报表中很难管理。用户在具# u+ A9 t% h& _. y+ x8 c
有系统生成主键的表内用副键进行检索往往会返回许多重复数据。 6 _, z3 j" r0 ?. M5 x U5 d4 C6 |; x3 E2 r: s
这样的检索性能比较低而且容易引起混乱。 " ]/ S, {% D, b; I 1 ]2 w7 e: W) f ■ 理解客户需求 v: |" O4 u# J) v) z$ t 1 \! ?5 U4 N3 p# V' V, [7 {# ?2 o 看起来这应该是显而易见的事,但需求就是来自客户(这里要从 7 j, u0 I3 ~7 _5 O8 N3 O 内部和外部客户的角度考虑)。不要依赖用户写下来的需求,真正的, y3 }5 O" Z3 x, d( g1 G
需求在客户的脑袋里。你要让客户解释其需求,而且随着开发的继续,! s, d* m2 H7 Y7 s- c
还要经常询问客户保证其需求仍然在开发的目的之中。一个不变的真9 q% w: v; |9 a0 w
理是:“只有我看见了我才知道我想要的是什么”必然会导致大量的 % ^- _0 w7 R6 C 返工,因为数据库没有达到客户从来没有写下来的需求标准。而更糟 " Q$ f' C! U8 ~: S$ o% Y1 P 的是你对他们需求的解释只属于你自己,而且可能是完全错误的。 U. [, ~2 e6 O1 M" z) B/ ~' {; a h) n
" ^) w- ~7 q& ?5 h7 ^8 o' L: g) F) Y! U , b4 {5 b! @! g1 N! u9 w
§ 第 2 部分 - 设计表和字段/ l' ]% w% t& `# E
──────────────' d: S6 V* c7 M& g8 Z" B
. d9 S, V% p% u% o
■ 检查各种变化' g$ d1 s) J; `& C; C* i# ]
/ F; Z8 ?7 g4 O. F
我在设计数据库的时候会考虑到哪些数据字段将来可能会发生变 . R5 x3 c6 R, T: o 更。比方说,姓氏就是如此(注意是西方人的姓氏,比如女性结婚后 " e. Z$ Y! f' c( k 从夫姓等)。所以,在建立系统存储客户信息时,我倾向于在单独的 & E0 C6 I$ i3 \$ @0 B 一个数据表里存储姓氏字段,而且还附加起始日和终止日等字段,这8 Y1 H m) ?( b/ d! K
样就可以跟踪这一数据条目的变化。 ( q2 ?: [4 @6 p: _$ s( b, K% ]: }. u+ P4 d1 B8 g
■ 采用有意义的字段名8 d" e4 {. _: ?7 F0 Q
: u: X2 x8 ~. d* j u0 [" w 有一回我参加开发过一个项目,其中有从其他程序员那里继承的 - k8 g Z. _" W7 ^6 [ 程序,那个程序员喜欢用屏幕上显示数据指示用语命名字段,这也不. ~: b$ \6 ]4 Q, j% c% B+ U
赖,但不幸的是,她还喜欢用一些奇怪的命名法,其命名采用了匈牙9 e3 |4 z2 v4 j2 d; L& |, U
利命名和控制序号的组合形式,比如 cbo1、txt2、txt2_b 等等。' K4 V% b4 r; @
" Q, O6 f* ?& e0 | 除非你在使用只面向你的缩写字段名的系统,否则请尽可能地把 # K) f1 Z( E8 s* V5 o4 l 字段描述的清楚些。当然,也别做过头了,比如 ( e1 T) V T* w/ t Customer_Shipping_Address_Street_Line_1,虽然很富有说明性, . P7 _( d4 {/ B+ f 但没人愿意键入这么长的名字,具体尺度就在你的把握中。9 v. k. |* d# `/ O9 I$ V