行迁移:当修改不是行链接的行时,当修改后的行长度大于修改前的行长度,并且该数据块中空闲空间不能完全容纳该行的数据时,就会发生行迁移。在这种情况下,oracle会将整行迁移到一个新的数据块上,而该行原先的空间只放一个指向新行位置的指针,并且该行原先空间的剩余空间不再被数据库使用,这些剩余空间称为空洞,这是产生表碎片的主要原因。注意发生行迁移的行的rowid不会变化,这也是引起数据库IO性能降低的原因。
行链接:当第一次插入行时,由于行太长而不能容纳在一个数据块时,会发生行链接。在这种情况下,oracle会使用与该块链接的一块或多块数据块来容纳该行的数据。引起行链接的情形通常是表上行记录的大小超出了数据库的块大小
1、 表上使用了LONG或LONG RAW数据类型
2、 表上多于255列
引起性能下降的原因主要是多余的IO造成的,当通过索引访问行迁移的行时,数据库
必须扫描一个以上的数据块
检测行迁移与行链接,通过带list chained rows选项的analyze语句识别,收集到指定表
Analyze table t list chained rows;
Select * from chained_row;
也可以通过检查v$sysstat视图中的”table fetch continued row”来检查行迁移与行链接
Select name,value from v$sysstat where name = ‘table fetch continued row
在大多数情况下,行链接是无法克服的,特别是在一个表中包含LONG、LOB等数据类型字段时。当在不同表中有大量链接行时,并且这些表的长度不是很长时,可以通过’更大的block size重建数据库的方法来解决
行迁移主要是设置的PCTFREE参数过小,导致没有给update操作留下足够的空闲空间。为了避免行迁移,需要设置合适的PCTFREE值,但会牺牲更多的空间为代价,而且只能缓解行迁移现象,不能完全解决,当设置了合适的PCTFREE后发现行迁移比较严重时,对表的数据进行重组。
重组脚本:
Drop table migrated_rows;
Drop table chained_rows;
@$ORACLE_HOME/rdbms/admin/utlchain.sql
Spool chained_row.txt
Analyze table t list chained rows;
Create table migrated_rows as
Select t.*
From t,chained_rows c
Where t.rowid = c.head_rowid
And c.table_name = upper(‘T’);
Delete from t where rowed in (select head_rowid from chained_rows where table_name = ‘T’);
Insert into t select * from migrated_rows;
Spool off
来自 “ ITPUB博客 ” ,链接:http://blog.itpub.net/25725504/viewspace-1179396/,如需转载,请注明出处,否则将追究法律责任。
转载于:http://blog.itpub.net/25725504/viewspace-1179396/