Wiederherstellen des logischen Speicherplatzes aus einem Tabellenbereich

11

Ich habe einen Tabellenbereich namens DATA, der mit der automatischen Erweiterung als false eingerichtet ist. Dieser Tabellenbereich verfügt über zwei Datendateien und ist so eingerichtet, dass er 350 GB physischen Speicherplatz beansprucht.

Vor einer Woche habe ich user_tablespaces und dba_data_files abgefragt und festgestellt, dass 20% des verfügbaren logischen Speicherplatzes vorhanden sind. Ich habe dann eine Bereinigung durchgeführt und viele Datensätze aus Tabellen in diesem Tabellenbereich entfernt. Wir hatten einen starken Anstieg des verfügbaren Platzes erwartet. Leider stellte ich bei der Abfrage der Ansichten fest, dass der verfügbare Speicherplatz jetzt 20,5% betrug.

Könnte dies an einer Datenfragmentierung liegen? Können wir den Tablespace irgendwie "defragmentieren" und den verlorenen Speicherplatz wiederherstellen? Oder müssen wir den Tablespace von Grund auf neu erstellen?

Nuno Furtado
quelle

Antworten:

14

Wenn Sie Datensätze löschen, wird das Segment durch nichts automatisch komprimiert. Daher müssen Sie eine Segmentverkleinerung durchführen, um den Speicherplatz zurückzugewinnen. Hier ist ein Auszug aus dem 11.2 Administratorhandbuch zur Rückgewinnung von verschwendetem Speicherplatz :

Im Laufe der Zeit können durch Aktualisierungen und Löschungen von Objekten in einem Tabellenbereich leere Bereiche entstehen, die einzeln nicht groß genug sind, um für neue Daten wiederverwendet zu werden. Diese Art von leerem Raum wird als fragmentierter freier Raum bezeichnet.

Objekte mit fragmentiertem freiem Speicherplatz können viel Speicherplatz verschwenden und die Datenbankleistung beeinträchtigen. Die bevorzugte Methode zum Defragmentieren und Zurückfordern dieses Speicherplatzes besteht darin, eine Online-Segmentverkleinerung durchzuführen. Dieser Prozess konsolidiert fragmentierten freien Raum unterhalb der Hochwassermarke und verdichtet das Segment. Nach der Verdichtung wird die Hochwassermarke verschoben, was zu einem neuen freien Raum über der Hochwassermarke führt. Dieser Raum über der Hochwassermarke wird dann freigegeben. Das Segment bleibt während des größten Teils des Vorgangs für Abfragen und DML verfügbar, und es muss kein zusätzlicher Speicherplatz zugewiesen werden.

Weiter unten auf derselben Seite können Sie Folgendes lesen:

Das Segmentschrumpfen ist eine Online-In-Place-Operation. DML-Operationen und Abfragen können während der Datenverschiebungsphase des Segmentschrumpfens ausgegeben werden. Gleichzeitige DML-Vorgänge werden am Ende des Verkleinerungsvorgangs für kurze Zeit blockiert, wenn der Speicherplatz freigegeben wird. Indizes werden während des Verkleinerungsvorgangs beibehalten und bleiben nach Abschluss des Vorgangs verwendbar. Für die Segmentverkleinerung muss kein zusätzlicher Speicherplatz zugewiesen werden.

Der Segmentschrumpf gewinnt nicht genutzten Platz über und unter der Hochwassermarke zurück. Im Gegensatz dazu wird durch die Freigabe von Speicherplatz nicht genutzter Speicherplatz nur oberhalb der Hochwassermarke zurückgewonnen. Bei Verkleinerungsvorgängen komprimiert die Datenbank standardmäßig das Segment, passt die Hochwassermarke an und gibt den zurückgewonnenen Speicherplatz frei.

Die Seite enthält viel mehr Informationen zu diesem Thema, einschließlich Beispiele.

Der Abschnitt "Segmentraum und Hochwassermarke" im Concepts Guide kann ebenfalls hilfreich sein.

Leigh Riffel
quelle
9

Ja, es wird an der Fragmentierung liegen.

Um den Speicherplatz zurückzugewinnen, rufen Sie zunächst eine Liste der Tabellen im Tabellenbereich mit der folgenden Abfrage ab (Partitionen ignorieren - Bearbeiten Sie Ihre Frage, wenn Sie sie verwenden):

select distinct table_name from dba_tables where tablespace_name = 'DATA';

Aktivieren Sie dann für jede Tabelle die Zeilenbewegung:

alter table TABLEINDATAPARTITION enable row movement;

Sie können dann die Tabelle verkleinern:

alter table TABLEINDATAPARTITION shrink space;

Verkleinern Sie dann die Datendateien mit:

alter database datafile '/path/to/my/file/data01.dbf' resize 20480M;

Die Datendateinamen können aus der DBA_DATA_FILESAnsicht abgerufen werden , die Sie bereits kennen.

Philᵀᴹ
quelle
Hervorragend, eine praktische Antwort. +1
Leigh Riffel