zoukankan      html  css  js  c++  java
  • Oracle-判断表上存在高水位线

    表上高水位线:通常一个新建的表,1个8K的数据块存放100行记录,若表上经常插入删除操作,造成表的水位线很高。下面从发现高水位线的办法,及解决高水位的方法说起:

    1、发现存在高水位线的表:查看字典表user_tables,该表分配的数据块blocks很多,然而记录数num_rows确很少。

    2、解决高水位的方法。

    -----------------------------------------------------------------------实验----------------------------------------------------------------------------------

    一、发现存在高水位线的表-经常有插入删除操作的表,水位线高,实验证明:

    1、查询表上的数据块大小
    SQL> set linesize 1000;
    SQL> col segment_name for a20
    SQL> select SEGMENT_NAME,BYTES/BLOCKS/1024 K from user_extents where SEGMENT_NAME='TEST_EMP' fetch first 1 rows only;
    
    SEGMENT_NAME                  K
    -------------------- ----------
    TEST_EMP                      8
    表上的数据块是8KB
    2、新建表,查看一个数据块存放多少行数据
    SQL> CREATE TABLE TEST_EMP
      2         (TEST_EMPNO NUMBER(4) not null,
      3  ENAME VARCHAR2(10),
      4  JOB VARCHAR2(9),
      5  MGR NUMBER(4),
      6  HIREDATE DATE,
      7  SAL NUMBER(7,2),
      8  COMM NUMBER(7,2),
      9  DEPTNO NUMBER(2) );
    
    表已创建。
    
    SQL> exec dbms_stats.gather_table_stats(ownname=>'META',tabname=>'TEST_EMP',estimate_percent=>10,method_opt=>'for all indexed columns',cascade=>TRUE);
    
    PL/SQL 过程已成功完成。
    --收集表上的统计信息
    
    SQL> select num_rows,blocks from user_tables where table_name='TEST_EMP';
    
      NUM_ROWS     BLOCKS
    ---------- ----------
             0          0
    --新建表blocks为0,num_rows为0;
    3、插入数据,多次插入
    SQL>INSERT INTO TEST_EMP VALUES
    (7369,'SMITH','CLERK',7902,to_date('17-12-1980','dd-mm-yyyy'),800,NULL,20);
    INSERT INTO TEST_EMP VALUES
    (7499,'ALLEN','SALESMAN',7698,to_date('20-2-1981','dd-mm-yyyy'),1600,300,30);
    INSERT INTO TEST_EMP VALUES
    (7521,'WARD','SALESMAN',7698,to_date('22-2-1981','dd-mm-yyyy'),1250,500,30);
    INSERT INTO TEST_EMP VALUES
    (7566,'JONES','MANAGER',7839,to_date('2-4-1981','dd-mm-yyyy'),2975,NULL,20);
    INSERT INTO TEST_EMP VALUES
    (7654,'MARTIN','SALESMAN',7698,to_date('28-9-1981','dd-mm-yyyy'),1250,1400,30);
    INSERT INTO TEST_EMP VALUES
    (7698,'BLAKE','MANAGER',7839,to_date('1-5-1981','dd-mm-yyyy'),2850,NULL,30);
    INSERT INTO TEST_EMP VALUES
    (7782,'CLARK','MANAGER',7839,to_date('9-6-1981','dd-mm-yyyy'),2450,NULL,10);
    INSERT INTO TEST_EMP VALUES
    (7788,'SCOTT','ANALYST',7566,to_date('13-JUL-87','dd-mm-rr')-85,3000,NULL,20);
    INSERT INTO TEST_EMP VALUES
    (7839,'KING','PRESIDENT',NULL,to_date('17-11-1981','dd-mm-yyyy'),5000,NULL,10);
    INSERT INTO TEST_EMP VALUES
    (7844,'TURNER','SALESMAN',7698,to_date('8-9-1981','dd-mm-yyyy'),1500,0,30);
    INSERT INTO TEST_EMP VALUES
    (7876,'ADAMS','CLERK',7788,to_date('13-JUL-87', 'dd-mm-rr')-51,1100,NULL,20);
    INSERT INTO TEST_EMP VALUES
    (7900,'JAMES','CLERK',7698,to_date('3-12-1981','dd-mm-yyyy'),950,NULL,30);
    INSERT INTO TEST_EMP VALUES
    (7902,'FORD','ANALYST',7566,to_date('3-12-1981','dd-mm-yyyy'),3000,NULL,20);
    INSERT INTO TEST_EMP VALUES
    (7934,'MILLER','CLERK',7782,to_date('23-1-1982','dd-mm-yyyy'),1300,NULL,10);
    SQL> insert into test_emp
      2  select * from test_emp;
    
    已创建 12 行。
    4、再次统计信息,获取数据块及记录条数
    SQL> exec dbms_stats.gather_table_stats(ownname=>'META',tabname=>'TEST_EMP',estimate_percent=>10,method_opt=>'for all indexed columns',cascade=>TRUE);
    
    PL/SQL 过程已成功完成。
    
    SQL> select num_rows,blocks from user_tables where table_name='TEST_EMP';
    
      NUM_ROWS     BLOCKS
    ---------- ----------
        392500       2386
    5、查看一个块存放多少记录
    SQL> select f,b,count(*) from (select dbms_rowid.rowid_relative_fno(rowid) f,dbms_rowid.rowid_block_number(rowid) b from test_emp)
       group by f,b;
             F          B   COUNT(*)
    ---------- ---------- ----------
            14    2568672        170
            14    2568676        170
            14    2568677        169
    已选择 2323 行。
    --一个块存放169行左右的数据

    至此,发现一个新建的表只有插入记录时,一个8K的数据块存放169行记录。test_emp表占用2386个数据块,记录行数392500。

    若此时执行删除操作,再次收集表上的统计信息,就会看到记录条数为0时,test_emp表占用的数据块仍然是2386块。此时就造成了test_emp表上的高水位线

    6、再次删除记录,查看test_emp占用的数据块
    SQL> delete from test_emp purge; 已删除 393216 行。 SQL> exec dbms_stats.gather_table_stats(ownname=>'META',tabname=>'TEST_EMP',estimate_percent=>10,method_opt=>'for all indexed columns',cascade=>TRUE); PL/SQL 过程已成功完成。 SQL> select num_rows,blocks from user_tables where table_name='TEST_EMP'; NUM_ROWS BLOCKS ---------- ---------- 0 2386

    故,8KB的数据块存放169行记录。若在字典表中看到test_emp表的num_rows与blocks差别太悬殊,则认为是高水位线。这是定性的方法,至于定量的还在研究中。

    二、解决高水位的方法:https://www.cnblogs.com/handhead/p/13158177.html

  • 相关阅读:
    Git的简单使用
    git中查看全部分支的命令
    ModuleNotFoundError: No module named '__main__.base'; '__main__' is not a package(即 if __name__=='__main__'的深入理解)
    django中使用filter()(即对QuerySet操作)时踩的坑
    django模型中如何创建数据并保存到数据库
    django中使用mysql创建索引时报错MySQL does not support a database index on longtext columns
    python环境的编码
    synchronized关键字以及实例锁 类锁
    深拷贝与浅拷贝
    java String不可变对象,但StringBuffer是可变对象
  • 原文地址:https://www.cnblogs.com/handhead/p/13218961.html
Copyright © 2011-2022 走看看