2

次のOracle SQLがあります。

Begin

-- tables
for c in (select table_name from user_tables) loop
execute immediate ('drop table '||c.table_name||' cascade constraints');
end loop;

-- sequences
for c in (select sequence_name from user_sequences) loop
execute immediate ('drop sequence '||c.sequence_name);
end loop;

End;

別の開発者から提供されたもので、どのように機能するのかわかりませんが、データベース内のすべてのテーブルが削除されます.

それは機能しますが、永遠にかかります!

スクリプト出力

すべてのテーブルを削除するのにそれほど時間がかかるとは思いません。どうしたんだ?そして、このスクリプトを改善できますか?

注:約 100 のテーブルがあります。

4

3 に答える 3

4

「うまくいきますが、永遠にかかります!」

この場合、永遠に 3 秒未満のテーブルを意味します :)

テーブルの削除には、テーブルを削除するだけではありません。制約、インデックス、トリガー、ロブまたはネストされたテーブル ストレージなど、削除する依存オブジェクトもあります。無効にするビュー、シノニム ストアド プロシージャがあります。取り消される助成金があります。テーブルのスペース (およびそのインデックスなどのスペース) の割り当てを解除する必要があります。

このアクティビティはすべて、データ ディクショナリから選択または更新するクエリである再帰 SQL を生成し、パフォーマンスが低下する可能性があります。トリガー、ビュー、ストアド プロシージャを使用しない場合でも、データベースはそれらが存在しないことを確認するためにクエリを実行する必要があります。

通常の SQL とは異なり、再帰 SQL を調整することはできませんが、環境を整えて実行を高速化することはできます。

これは、オブジェクトが定期的に構築および破棄される開発データベースであり、10g 以上を使用していると推測しています。

  1. ごみ箱を空にします。

    SQL> purge recyclebin;

  2. データ ディクショナリの統計を収集します (DBA 権限が必要です)。これらは、10g および 11g のデフォルトの動作であるため、すでに収集されている可能性があります。 詳細をご覧ください

  3. 辞書の統計を取得したら、コストベースのオプティマイザーを使用していることを確認してください。理想的には、これはデータベース レベルで設定する必要がありますが、セッション レベルで修正できます。

    SQL> alter session set optimizer_mode=choose;

于 2010-10-07T04:45:53.050 に答える
1

Purgeキーワードを使用するように DROP TABLE ステートメントを変更してみます。すべてのテーブルを削除しているため、同時に制約をカスケードする必要はありません。この動作がおそらく速度低下の原因です。ただし、これをテストする Oracle のインスタンスがないため、エラーが発生する可能性があります。

エラーがスローされたり、速度が速くならない場合は、Sequence ドロップ コマンドを削除して、どのコマンドが非常に時間がかかっているかを特定します。

DROP TABLE コマンドに関する Oracle のドキュメントはこちらです。

于 2010-10-07T01:34:42.313 に答える