re: 分享高性能批量插入和批量删除sql语句写法 知道得越多知道的越少 2008-09-28 14:59
"曾经测试过,这种写法插入1000条数据比循环调用1000次insert或1000条insert语句简单叠加一次调用要高效得多,大概快20多倍(调试状态不是太准)。其实很简单,就用了个union(union all 也可以),但当时得出测试结果时还是很惊喜的。"
循环调用1000次insert的时候,你没有用绑定变量方式吧,也没有用集合方式bulk collection,再forall方式插入吧.
大数据量的插入用绑定变量和批量处理的,意义在于减少SQL解析所花的时间,以及减少日志和回滚的产生.
re: 创建逻辑stand by数据库 知道得越多知道的越少 2007-11-03 00:34
阅
re: 对条件子句中带IN的SQL语句使用绑定变量 知道得越多知道的越少 2007-04-02 10:36
目前发现一个问题,在Oracle 817上使用需要注意一个BUG。
在使用In子句一个记录集表时,如果使用了Group by则会出现“通信信道结束”的错误。改为表联接方式就不会出现这个问题。
Where NO In (Select * From Table(Cast(f_Str2list('A01,A02,A03') As zlTools.t_Strlist)));
改为:
From 病人费用记录 A, Table(Cast(f_Str2list('A01,A02,A03') As zlTools.t_Strlist)) B
Where A.NO = B.Column_Value;
re: 对条件子句中带IN的SQL语句使用绑定变量 知道得越多知道的越少 2007-03-30 17:53
表名和字段名都是真实的汉字,实践表明没有什么不可以。
re: 2006总结之帖 --- 自己的2006颁奖典礼 知道得越多知道的越少 2007-01-15 11:22
充满机会的重庆欢迎你!
re: 电子病历与HIS的区别以及发展前途 知道得越多知道的越少 2006-12-21 17:42
"电子签名尚未实现,实现电子签名是一个复杂的技术和法律的混合问题。需要花很长的时间解决"
据我所知,目前南方和北方均有医院正式使用了电子签名,技术和法律问题都得到了解决.
re: 极光商智® 2005 昨日在北京隆重发布 知道得越多知道的越少 2006-12-14 13:22
支持!
re: 在Oracle中重编译所有无效的存储过程 知道得越多知道的越少 2006-10-18 09:18
其实PLSQL Developer中工具菜单下的编译无效对象非常方面,也更全面
re: 三层架构之我见 —— 不同于您见过的三层架构。 知道得越多知道的越少 2006-08-16 10:03
以前也觉得SQLHelper麻烦,明明一两三句就返回结果的,为什么要去搞那么多参数对象啊什么的.
后来了解了绑定变量才知道了原因.
小的应用看出不了反而麻烦,一但大的应用,使用三层好处就体现出来了.
re: HIS行业的技术先锋?先烈? 知道得越多知道的越少 2006-06-29 14:27
进度怎么样了,我最近也没有关注,可以在他们的博客上看看有没有新的消息:
http://www.agilelabs.cn
re: 位图索引深度探讨 知道得越多知道的越少 2006-05-29 18:19
下面的对比实验表明,使用位图索引时,由于访问的索引块少了很多,查询速度得到较大的提高
查询1087行数据,B树索引用了157块,CPU耗用0.05,位图索引用了82块,CPU耗用0.01
--使用B*Tree索引查询
SQL> drop index H票据使用明细_IX_领用ID;
SQL> create index H票据使用明细_IX_领用ID on H票据使用明细(领用ID);
SQL> Select * From H票据使用明细 Where 领用id=102;
已选择1087行。
Execution Plan
----------------------------------------------------------
0 SELECT STATEMENT Optimizer=CHOOSE
1 0 TABLE ACCESS (BY INDEX ROWID) OF 'H票据使用明细'
2 1 INDEX (RANGE SCAN) OF 'H票据使用明细_IX_领用ID' (NON-UNIQUE)
Statistics
----------------------------------------------------------
0 recursive calls
0 db block gets
157 consistent gets
0 physical reads
0 redo size
53393 bytes sent via SQL*Net to client
1295 bytes received via SQL*Net from client
74 SQL*Net roundtrips to/from client
0 sorts (memory)
0 sorts (disk)
1087 rows processed
Select *
From
H票据使用明细 Where 领用id=102
call count cpu elapsed disk query current rows
------- ------ -------- ---------- ---------- ---------- ---------- ----------
Parse 1 0.00 0.00 0 0 0 0
Execute 1 0.00 0.00 0 0 0 0
Fetch 74 0.01 0.05 2 157 0 1087
------- ------ -------- ---------- ---------- ---------- ---------- ----------
total 76 0.01 0.05 2 157 0 1087
Misses in library cache during parse: 1
Optimizer goal: ALL_ROWS
Parsing user id: 311
Rows Row Source Operation
------- ---------------------------------------------------
1087 TABLE ACCESS BY INDEX ROWID H票据使用明细
1087 INDEX RANGE SCAN H票据使用明细_IX_领用ID (object id 49919)
--使用位图索引查询
SQL> drop index H票据使用明细_IX_领用ID;
SQL> create bitmap index H票据使用明细_IX_领用ID on H票据使用明细(领用ID);
SQL> Select * From H票据使用明细 Where 领用id=102;
已选择1087行。
Execution Plan
----------------------------------------------------------
0 SELECT STATEMENT Optimizer=ALL_ROWS (Cost=3 Card=10 Bytes=1060)
1 0 TABLE ACCESS (BY INDEX ROWID) OF 'H票据使用明细' (Cost=3 Card=10 Bytes=1060)
2 1 BITMAP CONVERSION (TO ROWIDS)
3 2 BITMAP INDEX (SINGLE VALUE) OF 'H票据使用明细_IX_领用ID'
Statistics
----------------------------------------------------------
0 recursive calls
0 db block gets
82 consistent gets
0 physical reads
0 redo size
53393 bytes sent via SQL*Net to client
1295 bytes received via SQL*Net from client
74 SQL*Net roundtrips to/from client
0 sorts (memory)
0 sorts (disk)
1087 rows processed
Select *
From
H票据使用明细 Where 领用id=102
call count cpu elapsed disk query current rows
------- ------ -------- ---------- ---------- ---------- ---------- ----------
Parse 1 0.00 0.00 0 0 0 0
Execute 1 0.00 0.00 0 0 0 0
Fetch 74 0.01 0.01 0 82 0 1087
------- ------ -------- ---------- ---------- ---------- ---------- ----------
total 76 0.01 0.01 0 82 0 1087
Misses in library cache during parse: 0
Optimizer goal: ALL_ROWS
Parsing user id: 311
Rows Row Source Operation
------- ---------------------------------------------------
1087 TABLE ACCESS BY INDEX ROWID H票据使用明细
1087 BITMAP CONVERSION TO ROWIDS
1 BITMAP INDEX SINGLE VALUE H票据使用明细_IX_领用ID (object id 49920)
re: 位图索引深度探讨 知道得越多知道的越少 2006-05-29 13:47
Oracle 10G R2
下面的实验:
--修改索引的一个键值(更新或插入行),是否会更新关于该索引的所有键的位图
--a.更新或插入的行,在同一个块内
--b.更新或插入的行,不在同一个块内
SQL> alter table H病人挂号记录 add 备注 char(2000);
SQL> truncate table H病人挂号记录;
SQL> Insert Into H病人挂号记录(Id,No,号别,执行人) Values(1,'G000001',1,'张1');
SQL> Insert Into H病人挂号记录(Id,No,号别,执行人) Values(2,'G000002',1,'张2');
SQL> commit;
--此时的位图
SQL> alter system dump datafile 1 block 61434;
row#0[7988] flag: ------, lock: 2, len=27
col 0; len 3; (3): d5 c5 31 --键值'张1'
col 1; len 6; (6): 00 00 00 00 00 00 --rowid的起始位置
col 2; len 6; (6): 00 40 ef f2 00 07 --rowid的终止位置
col 3; len 6; (6): c0 d2 d5 dc bc 01 --位图
row#1[7940] flag: ------, lock: 2, len=27
col 0; len 3; (3): d5 c5 32
col 1; len 6; (6): 00 00 00 00 00 00
col 2; len 6; (6): 00 40 ef f2 00 07
col 3; len 6; (6): c1 d2 d5 dc bc 01
----- end of leaf block dump -----
End dump data blocks tsn: 0 file#: 1 minblk 61434 maxblk 61434
再插入一行键值为'张2'的,观察键值为'张1'的位图是否改变
SQL> Insert Into H病人挂号记录(Id,No,号别,执行人) Values(2,'G000002',1,'张2');
SQL> commit;
SQL> alter system dump datafile 1 block 61434;
row#0[7988] flag: ------, lock: 0, len=27
col 0; len 3; (3): d5 c5 31
col 1; len 6; (6): 00 00 00 00 00 00
col 2; len 6; (6): 00 40 ef f2 00 07
col 3; len 6; (6): c0 d2 d5 dc bc 01
row#1[7912] flag: ------, lock: 2, len=28
col 0; len 3; (3): d5 c5 32
col 1; len 6; (6): 00 00 00 00 00 00
col 2; len 6; (6): 00 40 ef f2 00 07
col 3; len 7; (7): f8 e4 d5 dc bc 01 06
----- end of leaf block dump -----
End dump data blocks tsn: 0 file#: 1 minblk 61434 maxblk 61434
--对比发现,索引键'张1'的位图c0 d2 d5 dc bc 01没有发生变化,
索引键'张2'的位图c1 d2 d5 dc bc 01变成了f8 e4 d5 dc bc 01 06
与8i的差别是,不用删除旧的位图,而是直接修改对应的索引键的位图来表示新的数据信息.
--b.更新或插入的行,不在同一个块内
SQL> exec show_space('H病人挂号记录','SYS','TABLE');
Free Blocks.............................1
Total Blocks............................8
Total Bytes.............................65536
Unused Blocks...........................6
Unused Bytes............................49152
Last Used Ext FileId....................1
Last Used Ext BlockId...................61425
Last Used Block.........................2
PL/SQL procedure successfully completed
--添加一列备注,添加5行信息,使表数据的存储超过1个块
SQL> Insert Into H病人挂号记录(Id,No,号别,执行人,备注) Values(1,'G000001',1,'张1',lpad('2000byte',2000,'*'));
1 row inserted
SQL> /
1 row inserted
SQL> /
1 row inserted
SQL> /
1 row inserted
SQL> /
1 row inserted
SQL> exec show_space('H病人挂号记录','SYS','TABLE');
Free Blocks.............................1
Total Blocks............................8
Total Bytes.............................65536
Unused Blocks...........................5
Unused Bytes............................40960
Last Used Ext FileId....................1
Last Used Ext BlockId...................61425
Last Used Block.........................3
PL/SQL procedure successfully completed
--对比前面的Last Used Block,由2变为了3,Unused Blocks由6变成了5,
说明高水标记已移动了一个块的位置.此时再插入数据,会放入块ID为61428的块中.
--先记下此时的索引块的情况
SQL> alter system dump datafile 1 block 61434;
row#0[7767] flag: ------, lock: 2, len=31
col 0; len 3; (3): d5 c5 31
col 1; len 6; (6): 00 00 00 00 00 00
col 2; len 6; (6): 00 40 ef f3 00 07
col 3; len 10; (10): f8 e4 d5 dc bc 01 39 f8 56 03
row#1[7912] flag: ------, lock: 0, len=28
col 0; len 3; (3): d5 c5 32
col 1; len 6; (6): 00 00 00 00 00 00
col 2; len 6; (6): 00 40 ef f2 00 07
col 3; len 7; (7): f8 e4 d5 dc bc 01 06
----- end of leaf block dump -----
End dump data blocks tsn: 0 file#: 1 minblk 61434 maxblk 61434
--再插入键值为'张2'的记录,注意,此时插入的记录已经不在该表以前的块上了(块号:61425+3)
SQL> Insert Into H病人挂号记录(Id,No,号别,执行人) Values(2,'G000002',1,'张2');
SQL> commit;
--索引的块没有变,仍是61434
SQL> alter system dump datafile 1 block 61434;
row#0[7767] flag: ------, lock: 0, len=31
col 0; len 3; (3): d5 c5 31
col 1; len 6; (6): 00 00 00 00 00 00
col 2; len 6; (6): 00 40 ef f3 00 07
col 3; len 10; (10): f8 e4 d5 dc bc 01 39 f8 56 03
row#1[7737] flag: ------, lock: 2, len=30
col 0; len 3; (3): d5 c5 32
col 1; len 6; (6): 00 00 00 00 00 00
col 2; len 6; (6): 00 40 ef f3 00 07
col 3; len 9; (9): f8 e4 d5 dc bc 01 06 c2 44
----- end of leaf block dump -----
End dump data blocks tsn: 0 file#: 1 minblk 61434 maxblk 61434
--与上面的比较发现,索引块内的位图行并没有增加,只是改变了位图f8 e4 d5 dc bc 01 06变成了f8 e4 d5 dc bc 01 06 c2 44
这一点,与8i区别很大,也就是说,10G中一个键值只有一个索引位图,
而8i中一个键值可能有一个或多个位图,单行数据插入时,每8行数据,或者当数据行分布在不同的数据块时,就会新建一个位图来记录.
是不是数据量少,才只有一个位图呢,下面再插入10000行数据的情况下,观察发现一个键值仍然只有一个位图.
一个位图索引块,由于采用位方式表示键值对应的数据,表达的数据是非常大的.
SQL> Declare
Begin
For i In 1..10000
Loop
Insert Into H病人挂号记录(Id,No,号别,执行人) Values(i,'G000001',1,'张1');
End Loop;
Commit;
End;
/
SQL> exec show_space('H病人挂号记录_IX_执行人','SYS','INDEX');
Free Blocks.............................0
Total Blocks............................8
Total Bytes.............................65536
Unused Blocks...........................6
Unused Bytes............................49152
Last Used Ext FileId....................1
Last Used Ext BlockId...................61433
Last Used Block.........................2
PL/SQL procedure successfully completed
SQL> alter system dump datafile 1 block 61434;
row#0[390] flag: ------, lock: 2, len=1530
col 0; len 3; (3): d5 c5 31
col 1; len 6; (6): 00 00 00 00 00 00
col 2; len 6; (6): 00 40 f3 27 00 67
col 3; len 1508; (1508):
ff e4 d5 dc bc 01 ff ff ff ff ff ff ff ff cf ff ff ff ff ff ff ff ff cf ff
ff ff ff ff ff ff ff cb ff ff ff 7f ff 3b ff ff ff ff ff ff ff ff cf ff ff
ff ff ff ff ff ff cf ff ff ff ff ff ff ff ff cb ff ff ff 0f ff 3b ff ff ff
ff ff ff ff ff cf ff ff ff ff ff ff ff ff cf ff ff ff ff ff ff ff ff cb ff
ff ff 0f ff 3b ff ff ff ff ff ff ff ff cf ff ff ff ff ff ff ff ff cf ff ff
ff ff ff ff ff ff cb ff ff ff 0f ff 3b ff ff ff ff ff ff ff ff cf ff ff ff
ff ff ff ff ff cf ff ff ff ff ff ff ff ff cb ff ff ff 0f ff 3b ff ff ff ff
ff ff ff ff cf ff ff ff ff ff ff ff ff cf ff ff ff ff ff ff ff ff cb ff ff
ff 0f ff 3b ff ff ff ff ff ff ff ff cf ff ff ff ff ff ff ff ff cf ff ff ff
ff ff ff ff ff cb ff ff ff 0f ff a3 06 ff ff ff ff ff ff ff ff cf ff ff ff
ff ff ff ff ff cf ff ff ff ff ff ff ff ff cb ff ff ff 0f ff 3b ff ff ff ff
ff ff ff ff cf ff ff ff ff ff ff ff ff cf ff ff ff ff ff ff ff ff cb ff ff
ff 0f ff 3b ff ff ff ff ff ff ff ff cf ff ff ff ff ff ff ff ff cf ff ff ff
ff ff ff ff ff cb ff ff ff 0f ff 3b ff ff ff ff ff ff ff ff cf ff ff ff ff
ff ff ff ff cf ff ff ff ff ff ff ff ff cb ff ff ff 0f ff 3b ff ff ff ff ff
ff ff ff cf ff ff ff ff ff ff ff ff cf ff ff ff ff ff ff ff ff cb ff ff ff
0f ff 3b ff ff ff ff ff ff ff ff cf ff ff ff ff ff ff ff ff cf ff ff ff ff
ff ff ff ff cb ff ff ff 0f ff 3b ff ff ff ff ff ff ff ff cf ff ff ff ff ff
ff ff ff cf ff ff ff ff ff ff ff ff cb ff ff ff 0f ff 3b ff ff ff ff ff ff
ff ff cf ff ff ff ff ff ff ff ff cf ff ff ff ff ff ff ff ff cb ff ff ff 0f
ff bb ae 04 ff ff ff ff ff ff ff ff cf ff ff ff ff ff ff ff ff cf ff ff ff
ff ff ff ff ff cb ff ff ff 0f ff 3b ff ff ff ff ff ff ff ff cf ff ff ff ff
ff ff ff ff cf ff ff ff ff ff ff ff ff cb ff ff ff 0f ff 3b ff ff ff ff ff
ff ff ff cf ff ff ff ff ff ff ff ff cf ff ff ff ff ff ff ff ff cb ff ff ff
0f ff 3b ff ff ff ff ff ff ff ff cf ff ff ff ff ff ff ff ff cf ff ff ff ff
ff ff ff ff cb ff ff ff 0f ff 3b ff ff ff ff ff ff ff ff cf ff ff ff ff ff
ff ff ff cf ff ff ff ff ff ff ff ff cb ff ff ff 0f ff 3b ff ff ff ff ff ff
ff ff cf ff ff ff ff ff ff ff ff cf ff ff ff ff ff ff ff ff cb ff ff ff 0f
ff 3b ff ff ff ff ff ff ff ff cf ff ff ff ff ff ff ff ff cf ff ff ff ff ff
ff ff ff cb ff ff ff 0f ff 3b ff ff ff ff ff ff ff ff cf ff ff ff ff ff ff
ff ff cf ff ff ff ff ff ff ff ff cb ff ff ff 0f ff 3b ff ff ff ff ff ff ff
ff cf ff ff ff ff ff ff ff ff cf ff ff ff ff ff ff ff ff cb ff ff ff 0f ff
3b ff ff ff ff ff ff ff ff cf ff ff ff ff ff ff ff ff cf ff ff ff ff ff ff
ff ff cb ff ff ff 0f ff 3b ff ff ff ff ff ff ff ff cf ff ff ff ff ff ff ff
ff cf ff ff ff ff ff ff ff ff cb ff ff ff 0f ff 3b ff ff ff ff ff ff ff ff
cf ff ff ff ff ff ff ff ff cf ff ff ff ff ff ff ff ff cb ff ff ff 0f ff 3b
ff ff ff ff ff ff ff ff cf ff ff ff ff ff ff ff ff cf ff ff ff ff ff ff ff
ff cb ff ff ff 0f ff 3b ff ff ff ff ff ff ff ff cf ff ff ff ff ff ff ff ff
cf ff ff ff ff ff ff ff ff cb ff ff ff 0f ff 3b ff ff ff ff ff ff ff ff cf
ff ff ff ff ff ff ff ff cf ff ff ff ff ff ff ff ff cb ff ff ff 0f ff 3b ff
ff ff ff ff ff ff ff cf ff ff ff ff ff ff ff ff cf ff ff ff ff ff ff ff ff
cb ff ff ff 0f ff 3b ff ff ff ff ff ff ff ff cf ff ff ff ff ff ff ff ff cf
ff ff ff ff ff ff ff ff cb ff ff ff 0f ff 3b ff ff ff ff ff ff ff ff cf ff
ff ff ff ff ff ff ff cf ff ff ff ff ff ff ff ff cb ff ff ff 0f ff 3b ff ff
ff ff ff ff ff ff cf ff ff ff ff ff ff ff ff cf ff ff ff ff ff ff ff ff cb
ff ff ff 0f ff 3b ff ff ff ff ff ff ff ff cf ff ff ff ff ff ff ff ff cf ff
ff ff ff ff ff ff ff cb ff ff ff 0f ff 3b ff ff ff ff ff ff ff ff cf ff ff
ff ff ff ff ff ff cf ff ff ff ff ff ff ff ff cb ff ff ff 0f ff 3b ff ff ff
ff ff ff ff ff cf ff ff ff ff ff ff ff ff cf ff ff ff ff ff ff ff ff cb ff
ff ff 0f ff 3b ff ff ff ff ff ff ff ff cf ff ff ff ff ff ff ff ff cf ff ff
ff ff ff ff ff ff cb ff ff ff 0f ff 3b ff ff ff ff ff ff ff ff cf ff ff ff
ff ff ff ff ff cf ff ff ff ff ff ff ff ff cb ff ff ff 0f ff 3b ff ff ff ff
ff ff ff ff cf ff ff ff ff ff ff ff ff cf ff ff ff ff ff ff ff ff cb ff ff
ff 0f ff 3b ff ff ff ff ff ff ff ff cf ff ff ff ff ff ff ff ff cf ff ff ff
ff ff ff ff ff cb ff ff ff 0f ff 3b ff ff ff ff ff ff ff ff cf ff ff ff ff
ff ff ff ff cf ff ff ff ff ff ff ff ff cb ff ff ff 0f ff 3b ff ff ff ff ff
ff ff ff cf ff ff ff ff ff ff ff ff cf ff ff ff ff ff ff ff ff cb ff ff ff
0f ff 3b ff ff ff ff ff ff ff ff cf ff ff ff ff ff ff ff ff cf ff ff ff ff
ff ff ff ff cb ff ff ff 0f ff 3b ff ff ff ff ff ff ff ff cf ff ff ff ff ff
ff ff ff cf ff ff ff ff ff ff ff ff cb ff ff ff 0f ff 3b ff ff ff ff ff ff
ff ff cc ff ff ff ff 01
----- end of leaf block dump -----
re: 位图索引深度探讨 知道得越多知道的越少 2006-05-29 13:46
oracle 8.1.7.0.0
下面的实验:
--修改索引的一个键值(更新或插入行),是否会更新关于该索引的所有键的位图
--a.更新或插入的行,在同一个块内
--b.更新或插入的行,不在同一个块内
Oracle 8i
SQL> alter table H病人挂号记录 add 备注 char(2000);
SQL> truncate table H病人挂号记录;
SQL> Insert Into H病人挂号记录(Id,No,号别,执行人) Values(1,'G000001',1,'张1');
SQL> Insert Into H病人挂号记录(Id,No,号别,执行人) Values(2,'G000002',1,'张2');
SQL> commit;
--此时的位图
SQL> alter system dump datafile 1 block 40028;
row#0[8008] flag: -----, lock: 2
col 0; len 3; (3): d5 c5 31 --键值'张1'
col 1; len 6; (6): 00 40 9c 54 00 00 --rowid的起始位置
col 2; len 6; (6): 00 40 9c 54 00 07 --rowid的终止位置
col 3; len 1; (1): 00 --位图,当一个段中,只有一条记录的时候,oracle不是采用bitmap映射的方式,而是直接给出这条记录在这个段中的位置。例如这里的00表示了这个段中的第一条记录
row#1[7986] flag: -----, lock: 2
col 0; len 3; (3): d5 c5 32
col 1; len 6; (6): 00 40 9c 54 00 00
col 2; len 6; (6): 00 40 9c 54 00 07
col 3; len 1; (1): 01
row#2[8030] flag: ---D-, lock: 2
col 0; NULL
col 1; NULL
col 2; NULL
col 3; NULL
----- end of leaf block dump -----
End dump data blocks tsn: 0 file#: 1 minblk 40028 maxblk 40028
再插入一行键值为'张2'的,观察键值为'张1'的位图是否改变
SQL> Insert Into H病人挂号记录(Id,No,号别,执行人) Values(2,'G000002',1,'张2');
SQL> commit;
SQL> alter system dump datafile 1 block 40028;
row#0[8008] flag: -----, lock: 0
col 0; len 3; (3): d5 c5 31
col 1; len 6; (6): 00 40 9c 54 00 00
col 2; len 6; (6): 00 40 9c 54 00 07
col 3; len 1; (1): 00
row#1[7986] flag: ---D-, lock: 2
col 0; len 3; (3): d5 c5 32
col 1; len 6; (6): 00 40 9c 54 00 00
col 2; len 6; (6): 00 40 9c 54 00 07
col 3; len 1; (1): 01
row#2[7963] flag: -----, lock: 2
col 0; len 3; (3): d5 c5 32
col 1; len 6; (6): 00 40 9c 54 00 00
col 2; len 6; (6): 00 40 9c 54 00 07
col 3; len 2; (2): c8 06
----- end of leaf block dump -----
End dump data blocks tsn: 0 file#: 1 minblk 40028 maxblk 40028
对比位图的变化,键值为'张1'的位图(row#0[8008])并没有变化
键值为'张2'的位图,索引块内新增加了一个位图行(row#2[7963]),用新的位图来表示插入的行,旧的索引位图(row#1[7986])做了删除标记.
与10G的差别是,先删除了旧的位图,再增加新的位图来表示.
--b.更新或插入的行,不在同一个块内
SQL> exec show_space('H病人挂号记录','SYS','TABLE');
Free Blocks.............................1
Total Blocks............................8
Total Bytes.............................65536
Unused Blocks...........................6
Unused Bytes............................49152
Last Used Ext FileId....................1
Last Used Ext BlockId...................40019
Last Used Block.........................2
PL/SQL procedure successfully completed
--添加一列备注,添加5行信息,使表数据的存储超过1个块
SQL> Insert Into H病人挂号记录(Id,No,号别,执行人,备注) Values(1,'G000001',1,'张1',lpad('2000byte',2000,'*'));
1 row inserted
SQL> /
1 row inserted
SQL> /
1 row inserted
SQL> /
1 row inserted
SQL> /
1 row inserted
SQL> exec show_space('H病人挂号记录','SYS','TABLE');
Free Blocks.............................1
Total Blocks............................8
Total Bytes.............................65536
Unused Blocks...........................5
Unused Bytes............................40960
Last Used Ext FileId....................1
Last Used Ext BlockId...................40019
Last Used Block.........................3
PL/SQL procedure successfully completed
--对比前面的Last Used Block,由2变为了3,Unused Blocks由6变成了5,说明高水标记已移动了一个块的位置.
此时再插入数据,会放入块ID为40021的块中.
--先记下此时的索引块的情况
SQL> alter system dump datafile 1 block 40028;
row#0[8008] flag: ---D-, lock: 2
col 0; len 3; (3): d5 c5 31
col 1; len 6; (6): 00 40 9c 54 00 00
col 2; len 6; (6): 00 40 9c 54 00 07
col 3; len 1; (1): 00
row#1[7940] flag: ---D-, lock: 2
col 0; len 3; (3): d5 c5 31
col 1; len 6; (6): 00 40 9c 54 00 00
col 2; len 6; (6): 00 40 9c 54 00 07
col 3; len 2; (2): c8 09
row#2[7917] flag: ---D-, lock: 2
col 0; len 3; (3): d5 c5 31
col 1; len 6; (6): 00 40 9c 54 00 00
col 2; len 6; (6): 00 40 9c 54 00 07
col 3; len 2; (2): c8 19
row#3[7894] flag: -----, lock: 2
col 0; len 3; (3): d5 c5 31
col 1; len 6; (6): 00 40 9c 54 00 00
col 2; len 6; (6): 00 40 9c 54 00 07
col 3; len 2; (2): c8 39
row#4[7872] flag: ---D-, lock: 2
col 0; len 3; (3): d5 c5 31
col 1; len 6; (6): 00 40 9c 55 00 00
col 2; len 6; (6): 00 40 9c 55 00 07
col 3; len 1; (1): 00
row#5[7849] flag: -----, lock: 2
col 0; len 3; (3): d5 c5 31
col 1; len 6; (6): 00 40 9c 55 00 00
col 2; len 6; (6): 00 40 9c 55 00 07
col 3; len 2; (2): c8 03
row#6[7963] flag: -----, lock: 0
col 0; len 3; (3): d5 c5 32
col 1; len 6; (6): 00 40 9c 54 00 00
col 2; len 6; (6): 00 40 9c 54 00 07
col 3; len 2; (2): c8 06
----- end of leaf block dump -----
End dump data blocks tsn: 0 file#: 1 minblk 40028 maxblk 40028
--以上数据可以发现,由于刚才插入了5条键值为"张1"(d5 c5 31)的记录,
索引块中的位图行,发生了5次变化,删除了4个位图行,最后,键值为'张1'的共有两个位图行.(7894,7849)
--再插入键值为'张2'的记录,注意,此时插入的记录已经不在该表以前的块上了(块号:40019+3)
SQL> Insert Into H病人挂号记录(Id,No,号别,执行人) Values(2,'G000002',1,'张2');
SQL> commit;
--索引的块没有变,仍是40028
SQL> alter system dump datafile 1 block 40028;
row#0[7894] flag: -----, lock: 0
col 0; len 3; (3): d5 c5 31
col 1; len 6; (6): 00 40 9c 54 00 00
col 2; len 6; (6): 00 40 9c 54 00 07
col 3; len 2; (2): c8 39
row#1[7849] flag: -----, lock: 0
col 0; len 3; (3): d5 c5 31
col 1; len 6; (6): 00 40 9c 55 00 00
col 2; len 6; (6): 00 40 9c 55 00 07
col 3; len 2; (2): c8 03
row#2[7963] flag: -----, lock: 2
col 0; len 3; (3): d5 c5 32
col 1; len 6; (6): 00 40 9c 54 00 00
col 2; len 6; (6): 00 40 9c 54 00 07
col 3; len 2; (2): c8 06
row#3[7827] flag: -----, lock: 2
col 0; len 3; (3): d5 c5 32
col 1; len 6; (6): 00 40 9c 55 00 00
col 2; len 6; (6): 00 40 9c 55 00 07
col 3; len 1; (1): 02
----- end of leaf block dump -----
End dump data blocks tsn: 0 file#: 1 minblk 40028 maxblk 40028
--与上面的比较发现,索引块内键值为"张2"的范围(7963)没有像上次增加5条键值为"张1"的那样被删除,而是只增加了新的段:7827
--这是因为新插入的数据行已经不在原来的块上,原有的索引块内的段位图已无法表示,需要索引块内用新的段位图来表示.
--另外,注意到由于新的索引数据的产生,以前插入5条记录时标记为删除(-D)的索引块内的段已经被回收.
--这一点与10G差别较大,10G中一个键值一直只有一个位图,即使键值对应的数据分布在不同的数据块中.
re: [随文杂记]星际争霸-感情重放 知道得越多知道的越少 2006-04-24 10:05
同感
re: 全表扫描比索引更慢吗?物理访问比逻辑读更慢吗? 知道得越多知道的越少 2006-04-06 14:14
Oracle 8i的优化模式缺省是Choose,即使你没有分析过表,Oracle仍然会在某些情况下选择CBO
上面这个例子就是这样,我并没有分析过表,但是Oracle却选择了CBO
Hash连接的好处与表的大小关系不大,主要是它是在用户区建立Hash矩阵来实现快速匹配.在并发下,可以大量减少栓锁.
而上面那个例子的索引扫描慢,是因为嵌套循环,每次循环对索引的读取的单块顺序读,因为索引范围扫描是对一个双向链表进行读,只能顺序读.
嵌套连接和Hash连接之所以慢,举个例子:
有1000个男的和1000个女的,按高矮进行配对跳舞.
如果用嵌套连接的话,在一个公用的广场上,有一个教练,他先对1000个男的和女的按高矮排序编号(建索引),再对1000个编号中的每一个(1000次循环),去匹配那些排好序的1000个女的编号,找到后,再根据编号去找他们的位置,一直牵手走出来。
如果这时,广场上有很多人,会很挤,可能排对进行,如果同时有很多教练要对这两千个人男女,进行同样的操作,就会形成争用,需要锁定和排队。
如果用Hash连接的话,这个教练它会找一个私有房间,把这些人的档案复印一份,直接对1000个男的和女的档案建立两个Hash矩阵图,这个图中记录这些人的位置,不用事先排序和编号,使用一种快速算法进行配对,配对完成后,再排序。如果同时有很多教练做相同的操作,他们都使用自己的私有房间,不会形成争用。
re: HIS行业的技术先锋?先烈? 知道得越多知道的越少 2006-04-06 10:09
@jackei
我并不是说卢彦现在的做法有什么问题.相反,他的作法确实很先进.
我对卢彦的才华和技术是很佩服的,并且他是一个很有思想的成熟程序员.只是觉得趟上HIS这混水,太不值得了.
如果选择了其它行业,成功不会这么辛苦.主要是中国的HIS没有规范,行业成熟度很低.需要很大的投入,付出很多艰辛,但是收获少,并且需要较长的周期.
re: HIS行业的技术先锋?先烈? 知道得越多知道的越少 2006-04-06 10:03
@[ IceSharK - PP.Poet ]
没有看过Cambio,不妨介绍一下.
估计是版太低。我是在8.1.7上成功的,记得还有init文件中的兼容参数也要改。
re: 也论该不该在项目中使用存储过程代替SQL语句 知道得越多知道的越少 2006-01-12 09:35
看大家说的都不是Oracle环境吧,难道SQL Server对存储过程的支持这么差
Oracle中使用存储过程的好处几乎不用证明.
re: 统一版本的诱惑 知道得越多知道的越少 2005-12-28 09:42
这种情况正和我们现在的情况类似,虽然不同是一个领域的,但都是专业应用软件开发.
问题分析得很透,但解决办法思考得不够.
开发商想的是如何用有限的人力满足更多的用户需求,以求成本的降低和效率的提高.
re: 思想篇(3)—IT运用模式的轮回 知道得越多知道的越少 2005-11-16 13:22
一般情况,管理人员因为不了解技术发展,不了解技术对产品的影响,多少会抱这种观点:认为技术不重要,重要的是对用户需求的理解和抽象.
并且一般情况,从开发成本和技术风险的角度考虑,管理人员不会去推动新技术的运用.
其实技术人员有责任去改动这种认识,去说服他们.
就象碗和筷子一样,都是为了吃饭,不存在哪个比哪个更重要的问题.
而是在各自的领域寻求最好的方法或工具,并考虑适当的时机.
re: 改错和功能增强详细设计 工作流程 知道得越多知道的越少 2005-11-16 09:50
其实就是产品维护规范及BUG管理系统
目前我们公司采用自己开发的一套BUG管理系统,基于工作流的方式实现了用户,技服人员,开发人员,测试人员等角色,在整个产品维护周期的管理.
规范包括程序编写规范,脚本编写规范,加上产品维护规范,通过这些规范,再加上管理系统,目前来看,比较适合公司的产品维护管理需求.
re: 来点入门级的:最近遇到的一些小问题及经验 知道得越多知道的越少 2005-05-26 10:32
估计博客园的高手也就那么十来个,处于金字塔顶端的必竟是少数.
所以发在这里是正确的,为大多数爱好者们一起交流经验.
况且,即便是高手,也会范一些低级错误的.基础的问题,不一定都知道的.
通过窗体的KeyPress 事件控制,这种方式确实更简单,但不便于控制有些需要按回车,但不是转到下一个控件的情况,例如,checkbox
还有更简单的,如果是ASP.net程序,直接在控件的网页中加这一句就可以了:
onkeydown="if (event.keyCode==13) event.keyCode=9;"
如果是Win Form程序,控件本身就有SelectNextControl方法,直接写一公共过程,把要处理的控件的KeyPress 事件重载指向这个公共过程就行了.
this.txtDays.KeyPress +=new KeyPressEventHandler(PressTabOnTextbox);
private void PressTabOnTextbox(object sender, System.Windows.Forms.KeyPressEventArgs e)
{
if (e.KeyChar ==(char)13)
{
this.SelectNextControl((Control)sender,true,true,true,true);
}
}
这种方式用来做练习还可以,单用户使用也不错.
并发使用不适合.
re: 数据库设计之“有时不得不违背的第三范式” 知道得越多知道的越少 2005-05-09 20:49
"有道理哟,想问一下,一个表里的字段数如果太多,你说有没有问题,比如有张表TestTable,里面包含了60多个字段,你认为这有不有问题?"
字段多不是问题,你可以去看看SPS的数据表Userdata,微软为每一种数据类型预留了64个字段,该表的字段数超过300个,记录数在100万条以上,也没有见严重影响性能.
很多时候,数据冗余是提升性能最有效的方法,特别是三个以上的表间联接,通过数据冗余来改善性能是非常明显的,同时也减小了SQL的复杂度.
re: VS.NET让我做了一场恶梦 知道得越多知道的越少 2005-03-28 22:40
有一个方法你可以试试,我现在的机器上没有.net环境。
直接在资源管理器中把.ascx文件拖到vs.net的解决方案资源管理器中
re: WebService安全性的问题 知道得越多知道的越少 2005-03-28 22:38
如果不是因为权限问题的话,可能需要对目录名加引号,因为CMD下遇到文件路径中有空格的情况都需要对整个目录加引号,你可以试一下,引号里再加引号。
re: 推荐两首好歌 知道得越多知道的越少 2005-03-22 13:36
收下.
如果服务程序用来启动一个有窗体的程序
请问自动怎么解决无法显示界面的问题,因为它是以LocalService等非当前用户启动的,无法显示进程界面.
该过去的总要过去,没办法啊.虽然我现在也不得不用VB6
re: Bug管理的流程和几个重点 知道得越多知道的越少 2005-03-04 13:54
bug管理如果不能和管理流程相结合,很难用起来.
所以,支持自定义流程的BUG管理系统才能适应这种需求.
如果bug只有状态管理,没有流程定制,就无法实现修改分配,测试分配,仲裁等功能.
re: 数据库主键设计之思考 知道得越多知道的越少 2005-03-03 10:39
还是Oracle有先见之明,从数据体本身的体系设计上为我们提供了好的方法,有sequences对象,每个表要用的主键建立对应的sequences,每次用时用.NEXTVAL和CURRVAL去取.也可以用触发器实现自动获取,灵活方便.
re: 几种主流网页开发语言的思考(上) 知道得越多知道的越少 2005-02-23 10:07
MSDE可以用SQL Server中的管理器,不过那个不是免费的.
re: C#利用CDOSYS组件发邮件的一些小结 知道得越多知道的越少 2005-02-05 09:30
就是反向域名检查,如果发现发件SMTP没有真实域名的话,他不收.
re: 在sql语句中替换Not In 的方法 知道得越多知道的越少 2005-02-04 09:42
还是Oracle好,可以用exists
select * from a where exists
(select 'x' from b where a.id=b.id)
re: .NET商业应用架构所要解决的若干问题(原创) 知道得越多知道的越少 2005-01-31 09:35
学习了,好文章.
re: 休学、退学与工作 知道得越多知道的越少 2005-01-27 13:18
支持,欢迎来重庆,有机会交流一下.
目前对.net比较感兴趣
微软的CRM中也有大量这种应用
界面上是通过Tab实现的,但代码不知道是什么方式实现的
微软的东西要处处想到拖
不知道大家是否知道这个:
多个图片也可以直接拖到解决方案资源管理器中
re: 逆向而行—ASP的O/R MAPPING 知道得越多知道的越少 2004-12-23 14:59
支持
用户的机器是NT4,不能强制他再投入改造,只能用ASP的情况很多.