Wprowadź nazwę schematu i nazwę obiektu (opcjonalnie) i kliknij Go
Użyj przycisku opcji, aby wybrać tabelę, na którą chcesz spojrzeć, i kliknij Edit(Nie klikaj linku nazwy tabeli)
Kliknij Segmentskartę (i poczekaj ...)
Zobaczysz rozmiar danych tabeli i zastosowane indeksy.
OK, to technicznie odpowiada na twoje pytanie. Ale lepszym sposobem jest:
Zaloguj się przy użyciu SQLPLUS
Uruchom skrypt z Vincenta.
Lubię zapisać skrypt jako t.sqlszybkie odniesienie
COLUMN size_mb FORMAT '999,999,990.0'
COLUMN num_rows FORMAT '999,999,990'
COLUMN fmt_short FORMAT A24
COLUMN owner FORMAT A16
COLUMN table_name LIKE fmt_short
COLUMN tablespace_name LIKE fmt_short
SET LINESIZE 200
SET AUTOTRACE OFF
COMPUTE SUM OF size_mb ON REPORT
BREAK ON REPORT
SELECT
lower( owner ) AS owner
,lower(table_name) AS table_name
,tablespace_name
,num_rows
,blocks*8/1024 AS size_mb
,pct_free
,compression
,logging
FROM all_tables
WHERE owner LIKE UPPER('&1')
OR owner = USER
ORDER BY 1,2;
CLEAR COMPUTES
CLEAR BREAKS
Nie jestem pewien, czy to zadziała, ponieważ nie uwzględnia indeksów, prawda?
Codek
1
@ Kodek: poprawne, jest to tylko przestrzeń używana przez samą tabelę. Możesz jednak obliczyć przestrzeń używaną przez indeksy tą samą metodą (ponieważ indeksy są segmentami i mają zakres).
Vincent
w rzeczy samej - jest to po prostu trudniejsze, ponieważ „nazwa” indeksu może być dowolna!
Codek
1
Działa to tylko w przypadku tabel, które nie mają kolumn LOB.
Czy jesteś pewien, że oryginalne podejście wykorzystujące widok all_tables obejmuje zakresy LOB? Nie sądzę. Oto jeden, który uważam za użyteczny:
with da as (
SELECT owner, segment_name, SUM(bytes)/1024/1024 size_mb
FROM dba_extents
group by rollup(owner, segment_name)
) select owner, segment_name, size_mb, round(size_mb/total_mb*100)
from da
cross join (
select size_mb as total_mb
from da t where owner is null and segment_name is null
)
order by size_mb desc
Po kilku wyszukiwaniach i eksperymentach w Google utworzyłem następujące zapytanie, które zapewnia moim zdaniem najdokładniejszy wynik. Dla użytkownika wyroczni zapewnia on wolne / używane / całkowite miejsce według typu tabeli i segmentu (TABELA *, INDEKS *, LOB *). Możesz go łatwo rozszerzyć, aby uzyskać dodatkowe statystyki, takie jak liczba bloków.
Typowe wyjście to:
table ; segment type ; used (mb) ; unused (mb) ; total (mb)
user ; INDEX ; 0,78; 0,00; 0,78
user ; LOBINDEX ; 0,15; 0,00; 0,15
user ; LOBSEGMENT ; 3,48; 1,19; 4,67
user ; TABLE ; 12,11; 2,74; 14,85
address ; INDEX ; 0,12; 0,00; 0,12
(...)
Scenariusz:
DECLARE
input_owner NVARCHAR2(128) := 'MY_ORACLE_OWNER';
segment_size_blocks NUMBER;
segment_size_bytes NUMBER;
used_blocks NUMBER;
used_bytes NUMBER;
expired_blocks NUMBER;
expired_bytes NUMBER;
unexpired_blocks NUMBER;
unexpired_bytes NUMBER;
total_blocks NUMBER;
total_bytes NUMBER;
unused_blocks NUMBER;
unused_bytes NUMBER;
last_ext_file_id NUMBER;
last_ext_blk_id NUMBER;
last_used_blk NUMBER;
result_table NVARCHAR2(128);
result_segment_type NVARCHAR2(128);
result_used_mb NUMBER;
result_unused_mb NUMBER;
result_total_mb NUMBER;
CURSOR cur
IS
SELECT
s.segment_name AS segment_name,
s.owner AS segment_owner,
s.partition_name AS partition_name,
s.segment_type AS segment_type,
CASE WHEN s.segment_type IN ('TABLE', 'TABLE PARTITION', 'TABLE SUBPARTITION')
THEN s.segment_name
WHEN s.segment_type IN ('INDEX', 'INDEX PARTITION', 'INDEX SUBPARTITION')
THEN (SELECT i.table_name
FROM dba_indexes i
WHERE s.segment_name = i.index_name AND s.owner = i.owner)
WHEN s.segment_type IN ('LOBSEGMENT', 'LOB PARTITION')
THEN (SELECT l.table_name
FROM dba_lobs l
WHERE s.segment_name = l.segment_name AND s.owner = l.owner)
WHEN s.segment_type IN ('LOBINDEX')
THEN (SELECT l.table_name
FROM dba_lobs l
WHERE s.segment_name = l.index_name AND s.owner = l.owner)
ELSE 'Unknown'
END AS table_name,
s.bytes AS segment_bytes
FROM dba_segments s
WHERE owner = input_owner
ORDER BY table_name, segment_type;
BEGIN
dbms_output.put_line('table ; segment type ; used (mb) ; unused (mb) ; total (mb)');
FOR ro IN cur
LOOP
result_table := ro.table_name;
result_segment_type := ro.segment_type;
IF ro.segment_type IN ('TABLE', 'INDEX')
THEN
dbms_space.unused_space(
segment_owner => ro.segment_owner,
segment_name => ro.segment_name,
segment_type => ro.segment_type,
total_blocks => total_blocks,
total_bytes => total_bytes,
unused_blocks => unused_blocks,
unused_bytes => unused_bytes,
last_used_extent_file_id => last_ext_file_id,
last_used_extent_block_id => last_ext_blk_id,
last_used_block => last_used_blk);
result_used_mb := (total_bytes - unused_bytes) / 1024 / 1024;
result_unused_mb := unused_bytes / 1024 / 1024;
result_total_mb := total_bytes / 1024 / 1024;
ELSIF ro.segment_type IN ('LOBSEGMENT')
THEN
dbms_space.space_usage(
segment_owner => ro.segment_owner,
segment_name => ro.segment_name,
segment_type => 'LOB',
partition_name => ro.partition_name,
segment_size_blocks => segment_size_blocks,
segment_size_bytes => segment_size_bytes,
used_blocks => used_blocks,
used_bytes => used_bytes,
expired_blocks => expired_blocks,
expired_bytes => expired_bytes,
unexpired_blocks => unexpired_blocks,
unexpired_bytes => unexpired_bytes
);
result_used_mb := used_bytes / 1024 / 1024;
result_unused_mb := (segment_size_bytes - used_bytes) / 1024 / 1024;
result_total_mb := segment_size_bytes / 1024 / 1024;
ELSE
-- TODO ??
result_used_mb := ro.segment_bytes / 1024 / 1024;
result_unused_mb := 0;
result_total_mb := result_used_mb + result_unused_mb;
END IF;
dbms_output.put_line(
RPAD(result_table, 30) || '; ' ||
RPAD(result_segment_type, 20)|| '; ' ||
TO_CHAR(result_used_mb / 1024 / 1024, '999999999990D00')|| '; ' ||
TO_CHAR(result_unused_mb / 1024 / 1024, '999999999990D00')|| '; ' ||
TO_CHAR(result_total_mb / 1024 / 1024, '999999999990D00'));
END LOOP;
END;
Odpowiedzi:
Przez OEM 10g,
Schema
zakładkęTables
łączu w obrębie obiektów bazy danychGo
Edit
(Nie klikaj linku nazwy tabeli)Segments
kartę (i poczekaj ...)OK, to technicznie odpowiada na twoje pytanie. Ale lepszym sposobem jest:
Lubię zapisać skrypt jako
t.sql
szybkie odniesienieźródło
Przestrzeń używana przez tabelę jest przestrzenią używaną przez wszystkie jej zakresy:
źródło
Czy jesteś pewien, że oryginalne podejście wykorzystujące widok all_tables obejmuje zakresy LOB? Nie sądzę. Oto jeden, który uważam za użyteczny:
Pokazuje mi, co zajmuje najwięcej miejsca.
źródło
Po kilku wyszukiwaniach i eksperymentach w Google utworzyłem następujące zapytanie, które zapewnia moim zdaniem najdokładniejszy wynik. Dla użytkownika wyroczni zapewnia on wolne / używane / całkowite miejsce według typu tabeli i segmentu (TABELA *, INDEKS *, LOB *). Możesz go łatwo rozszerzyć, aby uzyskać dodatkowe statystyki, takie jak liczba bloków.
Typowe wyjście to:
Scenariusz:
źródło