Oracle9i与ASE12.5分别是世界主流数据库厂商ORACLE、SYBASE公司的主打产品,拥有相当大的市场份额。本文抛开两者之间在体系结构、技术路线上的差异,纯粹从使用者的角度出发,整理了Oracle9i与SYBASE Adaptive Server Enterprise 12.5 (简称ASE12.5)相比的几个不足,至于ASE12.5与Oracle9i相比的不足则不在本文的讨论范围。 T~x|
,;E *f51$6
1 不支持正则表达式:熟悉Unix/Linux及ASE12.0/12.5的人都知道正则表达式的灵活、功能强大。像“查找所有包含数字的表名称”这样的需求,在ASE12.5中极其简单: po$Qq`vc
|!h%J"y
select name from sysobjects where type=”U” and name like “%[0-9]%” (这里sysobjects相当于Oracle9i中的all_objects),而Oracle9i的实现要颇费一番周折了,一般情况下很多人都是写一个函数实现,以下就是刚学Oracle的时候写的一个实现该功能的函数: ^b4hfH\[
DH< .P
CREATE OR REPLACE function is_number(p_str in varchar2) x~sgZ+wG
r=q=+-2 ua
return number K c?Ip v^M
k"0UwJ1V
as !B b3]z
9xE2\`Fk2
w_char char(1); "pDoMB?
pJU0PKT
i number :=1; xP;VyDB9
%VfpC_=Z
begin OqWdEX@ n
k}A (ybN
while i <= length(p_str) loop u:K T( G
N*iw ozJ]
w_char := substr(p_str,i,1); t^+D?`^
)U(k*CZY
if w_char >='0' and w_char <='9' then D <FDfG
ZRu|8A
return 1; iS`%.9y:
j,Xg+k;
end if; KINdMKa&B
;Hj Uy>IX
i:=i+1; S+ns.hU
?@3.m2e}
end loop; @MXXI{z~
6$D6@$L
return 0; XSLL&!W
V=H`;\Ys
end; ]AI)^5
p {1%Fw
/ ^Fz%-D3/
Y@:HVM
在Oracle9i调用一个自定义的PL/SQL函数开销会很大;远不及ASE12.5的内部实现。 5(hf $7N(
dFckFyU
2 UPDATE语句的“蹩脚”,在数据库的应用中,两个表关联update是很常见的,如有如下两个表:t_a(id,name,point,…),t_b(id,point,…) id均为主键或unique index,现要实现根据id的对应关系将t_b表上point加至t_a表point。我们来看Oracle9i与ASE12.5的实现: oQw2oOY
mu&X%(
/** For Oracle9i **/ xf`C/B
|Y!k6]Ue
Update t_a a $exV+
X}Wl1
Set a.point=a.point+(select b.point from t_b b where b.id=a.id) x$G<fQ {
`/{&VwW8vI
Where exists (select 1 from from t_ b where b.id=a.id) a4IWg3[
Y)jY9x
/ W+ >h` F
O XB.]$
/** For ASE12.0/12.5 **/ <hQT# ~i
dgnwHWu
Update t_a su+sD]:}g|
Ezu2@hQl
Set point=a.point+b.point ;@C\
?Z0b*vd%
From t_a a,t_b b `U)hCl-(k
/8LYGx6
Where a.id=b.id `&a.(%
]+KK g3l
Go Y(3J lApm
i *qAp[h)
Oracle9i的语句似乎不顾清晰、容易误解,而且查看执行计划发现t_b表或索引扫描了2遍!ASE12.5只扫描了1遍。虽然第2遍是逻辑读,但总觉得不甘心; tnBfebUt
mi2\N2
有时如果t_b表较小,且id上无索引,我宁愿采用cursor方式,多次试验表明 K)9EMO
.ED)WF*
比Create INDEX+关联UPDATE要快得多。还有就是采用Oracle9i的OLAP特性,用merge 语句来完成。 {r&f!n<Z
-07"GQZ8vd
3临时表技术的比较: pJ `8-p
1fM, ot:K
Ck8$TQ@
QY:xV$j&*
ITEM n +`y\pm
L15@f dp
存储位置 '?-Tz~
tqbl o^
DDL SI-eH
i1e$S [q
数据生命周期 )C%a,co
yBP6j
ORACLE9i I 4 +d AH_
J%-DwbAp|
任何表空间 Emhq%bIf^
%eVMMJr
用户自己维护,表名是全局(数据库用户)唯一 v/< x%sO
Ftz4.'
Session / Transaction v2_--,,x5
t@ "@;
ASE12.5 tl"Qm#A"
1jQ1^Y&p
Tempdb库 HWMuL, K
O:@I/4|rtX
用户create;用户drop或系统drop,表名Session级唯一 M"E^QT*qs
<,pH5q;Jx
Session djC.&G5U
sqj6*Y
C@YCr[
KMcudAFP7
*u l}|eDy
B` o_pC
Ym Qy}\"
]sPS*4.A)N
fL<CO.D
xWmo1t$
3'|;A`-
c)u|bl&n
虽然两者各有所长,但我觉得ASE12.5的实现似乎更得”临时”的精髓―在每个会话期间,“召之即来”,不用担心与别人重名,#11 #22 #aa #bb随个人喜好创建,”挥之即去”, 会话结束亦不必显式删除,由系统代劳,不必担心垃圾表存在。 \;.[]1
4BXYWYv"hY
4 Count的问题还是Distinct的问题?在select 语句使用 distinct 关键字修饰以返回唯一的行集,这在统计分析、剔除重复数据尤为重要,但是有时仅想统计一个总数呢?我第一次是这样写的: XnN\~f0
NX[~%D# Q
Select count(distinct a,b,c) from my_table 结果语法不对,只好修改为: nh>E(x4$I
x/C {1]9
Select count(*) from ( select distinct a,b,c from my_table ) 方得以通过,心想这一定是distinct惹的祸,但随后发现distinct 被冤枉了,因为即使是: %K@ngp>
?6[n;@>
Select count(a,b,c) from my_table 也是不行的。只能写成: j`j:HZ.
P k?X,C_v
Select count(*) from ( select a,b,c from my_table ) CX3uDXS
LfOq >G
但在ASE12.5上无论是Select count(distinct a,b,c) from my_table 还是Select count(a,b,c) from my_table 均能得出正确结果。 #{ gMJ
GR!]Qmq^P
5 数据导入导出工具的比较:Exp/Imp在备份和恢复方面用的比较多,且受版本(高低版本、32bit/64bit)、语言影响较大,且sqlldr 只能算作导入工具,严格来说Oracle9i没有表数据的文本级的导出工具!相反,ASE12.5的bcp 的在表数据导入导出方面的很灵活,格式也很简单,很容易做应用程序的输入。还有视图、存储过程、触发器的导出工具defncopy也很好用;至于Oracle9i,我N+1次遇到以下情况: 6n\qnh$0.
f5R'9 3f#
问:我怎么得到某个存储过程的代码啊? A#Qu-i ,s
S>eOme
答:有没有装client阿? m8:GDB"qGi
:l[h=.N,
问:装了! 7U=g >tg
>(uWu^]1
答:打开Enterprise Manager Console,登录后在方案下面找吧 \0.<O-R'
7rAX
…… 3/O/XA"9
X_?DV
问:怎么麻烦阿? k -v:E!
=&+v][cG
答:那你有没有装Toad或者PL/Develop阿,这些工具好用点 [%Gi 1kU
r1AOyf
问:没有啊! j8OF<Qo]
dksRu8(.
答:L gH96;~7
8D:>U1gLW
或者 sf^F^ Bio
#@($`qd_u
问:我怎么得到某个存储过程的代码啊? |mZ "@L
pJV,1s
答:有没有装client阿? LN)E>w}d
ylWO2H
问:装了,可我在主机上啊! 0n!@NWo6
~n Vd$
答:那你用sqlplus看罢, j}A+gNH'd
3 &V,uJW
set long 300 hGk`L#
"2_8fkT>o
select text from all_source where name=’YourName’ #V GG
r3SMhW
go s/7 ShQ-R
hE[G;sP
问:哇,怎么麻烦阿 wdf6GCca
=f?BXOo`s'
答:L {P^m,WVb
0QG\{&I7*
要是在ASE12.0 ?'<qcLA
q^c3sZ
问:我怎么得到某个存储过程的代码啊? k6kQ
|pa9Kc |!
答:用defncopy 吧 ouyS#b87P(
q|Ea"F
问:怎么用啊 ~b6tAr1/
7dd7
答:我靠,这么简单!你还用问阿!J OdB6|?<6$
K/ t:]"
6 联机备份:虽然Oracle9i提供了冷、热备份技术,但是与ASE12.5基于Open Server技术的联机实时备份Backup Server相比似乎逊色不少,将备份的介质直接拿到另外一台ASE12.5进行Load,很快很简单就能获得一个时效性极强的”镜像”数据库环境。而我觉得Exp/Imp比较琐碎,且限制也较多。 1zrdZM(n
} 8xHI%gp
Oracle9i附带的命令行工具如sqlplus exp/imp sqlldr等,执行时无一例外都将输出时间、版本、版权信息,给像我这样喜欢用shell处理结果的人来说徒增不少麻烦,相比ASE12.5的isql bcp defncopy 的干净利落,是Oracle9i的无聊和”自恋”,还是埃里克森的霸气呢? ?vobY:Mpx
,;E *f51$6
1 不支持正则表达式:熟悉Unix/Linux及ASE12.0/12.5的人都知道正则表达式的灵活、功能强大。像“查找所有包含数字的表名称”这样的需求,在ASE12.5中极其简单: po$Qq`vc
|!h%J"y
select name from sysobjects where type=”U” and name like “%[0-9]%” (这里sysobjects相当于Oracle9i中的all_objects),而Oracle9i的实现要颇费一番周折了,一般情况下很多人都是写一个函数实现,以下就是刚学Oracle的时候写的一个实现该功能的函数: ^b4hfH\[
DH< .P
CREATE OR REPLACE function is_number(p_str in varchar2) x~sgZ+wG
r=q=+-2 ua
return number K c?Ip v^M
k"0UwJ1V
as !B b3]z
9xE2\`Fk2
w_char char(1); "pDoMB?
pJU0PKT
i number :=1; xP;VyDB9
%VfpC_=Z
begin OqWdEX@ n
k}A (ybN
while i <= length(p_str) loop u:K T( G
N*iw ozJ]
w_char := substr(p_str,i,1); t^+D?`^
)U(k*CZY
if w_char >='0' and w_char <='9' then D <FDfG
ZRu|8A
return 1; iS`%.9y:
j,Xg+k;
end if; KINdMKa&B
;Hj Uy>IX
i:=i+1; S+ns.hU
?@3.m2e}
end loop; @MXXI{z~
6$D6@$L
return 0; XSLL&!W
V=H`;\Ys
end; ]AI)^5
p {1%Fw
/ ^Fz%-D3/
Y@:HVM
在Oracle9i调用一个自定义的PL/SQL函数开销会很大;远不及ASE12.5的内部实现。 5(hf $7N(
dFckFyU
2 UPDATE语句的“蹩脚”,在数据库的应用中,两个表关联update是很常见的,如有如下两个表:t_a(id,name,point,…),t_b(id,point,…) id均为主键或unique index,现要实现根据id的对应关系将t_b表上point加至t_a表point。我们来看Oracle9i与ASE12.5的实现: oQw2oOY
mu&X%(
/** For Oracle9i **/ xf`C/B
|Y!k6]Ue
Update t_a a $exV+
X}Wl1
Set a.point=a.point+(select b.point from t_b b where b.id=a.id) x$G<fQ {
`/{&VwW8vI
Where exists (select 1 from from t_ b where b.id=a.id) a4IWg3[
Y)jY9x
/ W+ >h` F
O XB.]$
/** For ASE12.0/12.5 **/ <hQT# ~i
dgnwHWu
Update t_a su+sD]:}g|
Ezu2@hQl
Set point=a.point+b.point ;@C\
?Z0b*vd%
From t_a a,t_b b `U)hCl-(k
/8LYGx6
Where a.id=b.id `&a.(%
]+KK g3l
Go Y(3J lApm
i *qAp[h)
Oracle9i的语句似乎不顾清晰、容易误解,而且查看执行计划发现t_b表或索引扫描了2遍!ASE12.5只扫描了1遍。虽然第2遍是逻辑读,但总觉得不甘心; tnBfebUt
mi2\N2
有时如果t_b表较小,且id上无索引,我宁愿采用cursor方式,多次试验表明 K)9EMO
.ED)WF*
比Create INDEX+关联UPDATE要快得多。还有就是采用Oracle9i的OLAP特性,用merge 语句来完成。 {r&f!n<Z
-07"GQZ8vd
3临时表技术的比较: pJ `8-p
1fM, ot:K
Ck8$TQ@
QY:xV$j&*
ITEM n +`y\pm
L15@f dp
存储位置 '?-Tz~
tqbl o^
DDL SI-eH
i1e$S [q
数据生命周期 )C%a,co
yBP6j
ORACLE9i I 4 +d AH_
J%-DwbAp|
任何表空间 Emhq%bIf^
%eVMMJr
用户自己维护,表名是全局(数据库用户)唯一 v/< x%sO
Ftz4.'
Session / Transaction v2_--,,x5
t@ "@;
ASE12.5 tl"Qm#A"
1jQ1^Y&p
Tempdb库 HWMuL, K
O:@I/4|rtX
用户create;用户drop或系统drop,表名Session级唯一 M"E^QT*qs
<,pH5q;Jx
Session djC.&G5U
sqj6*Y
C@YCr[
KMcudAFP7
*u l}|eDy
B` o_pC
Ym Qy}\"
]sPS*4.A)N
fL<CO.D
xWmo1t$
3'|;A`-
c)u|bl&n
虽然两者各有所长,但我觉得ASE12.5的实现似乎更得”临时”的精髓―在每个会话期间,“召之即来”,不用担心与别人重名,#11 #22 #aa #bb随个人喜好创建,”挥之即去”, 会话结束亦不必显式删除,由系统代劳,不必担心垃圾表存在。 \;.[]1
4BXYWYv"hY
4 Count的问题还是Distinct的问题?在select 语句使用 distinct 关键字修饰以返回唯一的行集,这在统计分析、剔除重复数据尤为重要,但是有时仅想统计一个总数呢?我第一次是这样写的: XnN\~f0
NX[~%D# Q
Select count(distinct a,b,c) from my_table 结果语法不对,只好修改为: nh>E(x4$I
x/C {1]9
Select count(*) from ( select distinct a,b,c from my_table ) 方得以通过,心想这一定是distinct惹的祸,但随后发现distinct 被冤枉了,因为即使是: %K@ngp>
?6[n;@>
Select count(a,b,c) from my_table 也是不行的。只能写成: j`j:HZ.
P k?X,C_v
Select count(*) from ( select a,b,c from my_table ) CX3uDXS
LfOq >G
但在ASE12.5上无论是Select count(distinct a,b,c) from my_table 还是Select count(a,b,c) from my_table 均能得出正确结果。 #{ gMJ
GR!]Qmq^P
5 数据导入导出工具的比较:Exp/Imp在备份和恢复方面用的比较多,且受版本(高低版本、32bit/64bit)、语言影响较大,且sqlldr 只能算作导入工具,严格来说Oracle9i没有表数据的文本级的导出工具!相反,ASE12.5的bcp 的在表数据导入导出方面的很灵活,格式也很简单,很容易做应用程序的输入。还有视图、存储过程、触发器的导出工具defncopy也很好用;至于Oracle9i,我N+1次遇到以下情况: 6n\qnh$0.
f5R'9 3f#
问:我怎么得到某个存储过程的代码啊? A#Qu-i ,s
S>eOme
答:有没有装client阿? m8:GDB"qGi
:l[h=.N,
问:装了! 7U=g >tg
>(uWu^]1
答:打开Enterprise Manager Console,登录后在方案下面找吧 \0.<O-R'
7rAX
…… 3/O/XA"9
X_?DV
问:怎么麻烦阿? k -v:E!
=&+v][cG
答:那你有没有装Toad或者PL/Develop阿,这些工具好用点 [%Gi 1kU
r1AOyf
问:没有啊! j8OF<Qo]
dksRu8(.
答:L gH96;~7
8D:>U1gLW
或者 sf^F^ Bio
#@($`qd_u
问:我怎么得到某个存储过程的代码啊? |mZ "@L
pJV,1s
答:有没有装client阿? LN)E>w}d
ylWO2H
问:装了,可我在主机上啊! 0n!@NWo6
~n Vd$
答:那你用sqlplus看罢, j}A+gNH'd
3 &V,uJW
set long 300 hGk`L#
"2_8fkT>o
select text from all_source where name=’YourName’ #V GG
r3SMhW
go s/7 ShQ-R
hE[G;sP
问:哇,怎么麻烦阿 wdf6GCca
=f?BXOo`s'
答:L {P^m,WVb
0QG\{&I7*
要是在ASE12.0 ?'<qcLA
q^c3sZ
问:我怎么得到某个存储过程的代码啊? k6kQ
|pa9Kc |!
答:用defncopy 吧 ouyS#b87P(
q|Ea"F
问:怎么用啊 ~b6tAr1/
7dd7
答:我靠,这么简单!你还用问阿!J OdB6|?<6$
K/ t:]"
6 联机备份:虽然Oracle9i提供了冷、热备份技术,但是与ASE12.5基于Open Server技术的联机实时备份Backup Server相比似乎逊色不少,将备份的介质直接拿到另外一台ASE12.5进行Load,很快很简单就能获得一个时效性极强的”镜像”数据库环境。而我觉得Exp/Imp比较琐碎,且限制也较多。 1zrdZM(n
} 8xHI%gp
Oracle9i附带的命令行工具如sqlplus exp/imp sqlldr等,执行时无一例外都将输出时间、版本、版权信息,给像我这样喜欢用shell处理结果的人来说徒增不少麻烦,相比ASE12.5的isql bcp defncopy 的干净利落,是Oracle9i的无聊和”自恋”,还是埃里克森的霸气呢? ?vobY:Mpx
闽公网安备 35060202000074号