量産メモ帳

忘れっぽいのでメモを残しています。浅く適当に書きます。

テーブルとインデックスの使用率を調べる。

スポンサーリンク

だいぶ前の話だけど、こちらの記事がとても参考になりました。



万が一、ページが削除された場合に備えて加筆・引用させていただきます。


CLEAR BUFFER
SET NEWPAGE NONE
SET SPACE 1
SET ECHO OFF
SET FEEDBACK OFF
SET VERIFY OFF
SET SERVEROUTPUT ON SIZE 1000000
SET LINESIZE 300
SET HEAD OFF
SET PAGESIZE 9999
SET RECSEP OFF

DECLARE
V_TOTAL_BLOCKS NUMBER;
V_TOTAL_BYTES NUMBER;
V_UNUSED_BLOCKS NUMBER;
V_UNUSED_BYTES NUMBER;
V_LAST_USED_EXTENT_FILE_ID NUMBER;
V_LAST_USED_EXTENT_BLOCK_ID NUMBER;
V_LAST_USED_BLOCK NUMBER;
V_OWNER VARCHAR2(30);
V_OBJECT_NAME VARCHAR2(30);
V_SUBOBJECT_NAME VARCHAR2(30);
V_OBJECT_TYPE VARCHAR2(16);
V_OBJECT_NAME2 CHAR(30);
V_SUBOBJECT_NAME2 CHAR(30);
V_OBJECT_TYPE2 CHAR(16);
V_TOTAL_SIZE NUMBER;
V_USED_SIZE NUMBER;
V_UNUSED_SIZE NUMBER;
V_USED_RATE NUMBER;
C_TOTAL_SIZE CHAR(14);
C_USED_SIZE CHAR(14);
C_UNUSED_SIZE CHAR(14);
C_USED_RATE CHAR(9);
CURSOR CUR1 IS
SELECT OWNER, SEGMENT_NAME, SEGMENT_TYPE, PARTITION_NAME
FROM DBA_EXTENTS
WHERE (SEGMENT_TYPE LIKE 'TABLE%' OR SEGMENT_TYPE LIKE 'INDEX%') AND
OWNER = UPPER('&1')
GROUP BY OWNER, SEGMENT_NAME, SEGMENT_TYPE, PARTITION_NAME;

BEGIN

DBMS_OUTPUT.PUT_LINE('オブジェクト名         パーティション名        オブジェクト種別 全体サイズ(KB) 使用サイズ(KB) 空きサイズ(KB) 使用率(%)');

FOR CUR1_REC IN CUR1 LOOP
V_OWNER := CUR1_REC.OWNER;
V_OBJECT_NAME := CUR1_REC.SEGMENT_NAME;
V_SUBOBJECT_NAME := CUR1_REC.PARTITION_NAME;
V_OBJECT_TYPE := CUR1_REC.SEGMENT_TYPE;

DBMS_SPACE.UNUSED_SPACE(
SEGMENT_OWNER=>V_OWNER, SEGMENT_NAME=>V_OBJECT_NAME, SEGMENT_TYPE=>V_OBJECT_TYPE,
TOTAL_BLOCKS => V_TOTAL_BLOCKS, TOTAL_BYTES => V_TOTAL_BYTES,
UNUSED_BLOCKS => V_UNUSED_BLOCKS, UNUSED_BYTES => V_UNUSED_BYTES,
LAST_USED_EXTENT_FILE_ID => V_LAST_USED_EXTENT_FILE_ID,
LAST_USED_EXTENT_BLOCK_ID => V_LAST_USED_EXTENT_BLOCK_ID,
LAST_USED_BLOCK => V_LAST_USED_BLOCK,
PARTITION_NAME => V_SUBOBJECT_NAME);

V_OBJECT_NAME2 := V_OBJECT_NAME;
V_SUBOBJECT_NAME2 := NVL(V_SUBOBJECT_NAME, ' ');
V_OBJECT_TYPE2 := V_OBJECT_TYPE;
V_TOTAL_SIZE := V_TOTAL_BLOCKS * &2;
V_USED_SIZE := (V_TOTAL_BLOCKS - V_UNUSED_BLOCKS) * &2;
V_UNUSED_SIZE := V_UNUSED_BLOCKS * &2;
V_USED_RATE := V_USED_SIZE / V_TOTAL_SIZE * 100;
C_TOTAL_SIZE := TO_CHAR(V_TOTAL_SIZE, '9,999,999,990');
C_USED_SIZE := TO_CHAR(V_USED_SIZE, '9,999,999,990');
C_UNUSED_SIZE := TO_CHAR(V_UNUSED_SIZE, '9,999,999,990');
C_USED_RATE := TO_CHAR(V_USED_RATE, '999990.0');

DBMS_OUTPUT.PUT_LINE(V_OBJECT_NAME2 || ' ' || V_SUBOBJECT_NAME2 || ' ' || V_OBJECT_TYPE2 || ' ' || C_TOTAL_SIZE || ' ' || C_USED_SIZE || ' ' || C_UNUSED_SIZE || ' ' || C_USED_RATE);

END LOOP ;
END;
/



Oracle 8i の頃のやり方なので、Oracle 11g では一部は非推奨だった記憶がありますけど、具体的な内容は忘れました。