1

私はPostgreSQL8.4.13データベースを使用しています。
最近、テーブルに約8650万件のレコードがありました。私はそれらのほとんどすべてを削除しました-現在5000レコードしか残っていません。私は走った:

vacuum full

行を削除した後、ディスクスペースをOSに戻しました(仲間のSOメンバーからの提案へのthx

しかし、私のID番号はまだ数百万にとどまっていることがわかります。例:

    id   |        date_time        | event_id | secs_since_1970 |    value 
---------+-------------------------+----------+-----------------+-----------
61216287 | 2013/03/18 16:42:42:041 |        6 |   1363646562.04 |   46.4082
61216289 | 2013/03/18 16:42:43:041 |        6 |   1363646563.04 |   55.4496
61216290 | 2013/03/18 16:42:44:041 |        6 |   1363646564.04 |   40.0553
61216291 | 2013/03/18 16:42:45:041 |        6 |   1363646565.04 |   38.5694

残りの行のid値を最初からやり直すために、次のことを試みました。1

cluster mytable_pkey on mytable;

mytable私のテーブルの名前はどこですか。しかし、それは役に立ちませんでした。だから、私の質問は/です:

  1. インデックス(id値)を1から再開する方法はありますか?
  2. 新しいレコードでテーブルを追加または更新した場合、テーブルは1から開始しますか、それとも次に大きい整数値(上記の例では61216292)を取得しますか?

私のテーブルの説明は次のとおりです。FK制約もシーケンスもありません。

jbossql=> \d mytable;
           Table "public.mytable"
 Column      |          Type          | Modifiers 
-----------------+------------------------+-----------
 id              | bigint                 | not null
 date_time       | character varying(255) | 
 event_id        | bigint                 | 
 secs_since_1970 | double precision       | 
 value           | real                   | 
Indexes:
    "mydata_pkey" PRIMARY KEY, btree (id) CLUSTER
4

3 に答える 3

2

主キーfisrtを削除し、一時的なシーケンスを作成します。

alter table mytable drop constraint mydata_pkey;
create temporary sequence temp_seq;

シーケンスを使用して更新します。

update mytable
set id = nextval('temp_seq');

主キーを再作成し、シーケンスを削除します

alter table mytable add primary key (id);
drop sequence temp_seq;

このテーブルに外部キーの依存関係がある場合は、最初にそれを処理する必要があり、更新はより複雑な手順になります。

于 2013-03-21T11:31:39.363 に答える
2

主キーはシリアルを使用して定義されていますか?もしそうなら、それは暗黙のシーケンスを作成します。ALTER SEQUENCE(構文についてはhttp://www.postgresql.org/docs/8.2/static/sql-altersequence.htmlを参照)を使用して、開始番号を1に戻すことができます。

いくつかのレコードが残っているという事実に基づいて(5000が残っていることに気づきました)、そのシーケンスが一意でない番号を生成するため、残りのレコードの最後のIDの前の番号にその番号をリセットしたくありません。シーケンスを使用するポイントは、数値をインクリメントするトランザクションの方法を提供し、連続する操作が一意のインクリメントされた数値を取得することを保証することです。

于 2013-03-20T15:21:26.977 に答える
2
DROP SCHEMA tmp CASCADE;
CREATE SCHEMA tmp ;
SET search_path=tmp;

        --
        -- Note: "deferrable initially deferred" appears to be the default
        --
CREATE TABLE funky
        ( id SERIAL NOT NULL PRIMARY KEY DEFERRABLE INITIALLY DEFERRED
        , tekst varchar
        );
        -- create some data with gaps in it
INSERT INTO funky(id, tekst)
SELECT  gs, 'Number:' || gs::text
FROM generate_series(1,100,10) gs
        ;

        -- set the sequence to the max occuring id
SELECT setval('funky_id_seq' , mx.mx)
FROM (SELECT max(id) AS mx FROM funky) mx
        ;

SELECT * FROM funky ;

        -- compress the keyspace, making the ids consecutive
UPDATE funky xy
SET id =  self.newid
FROM (
        SELECT id AS id
        , row_number() OVER (ORDER BY id) AS newid
        FROM funky
        ) self
WHERE self.id = xy.id
        ;

        -- set the sequence to the new max occuring id
SELECT setval('funky_id_seq' , mx.mx)
FROM (SELECT max(id) AS mx FROM funky) mx
        ;

SELECT * FROM funky ;

結果:

CREATE TABLE
INSERT 0 10
 setval 
--------
     91
(1 row)

 id |   tekst   
----+-----------
  1 | Number:1
 11 | Number:11
 21 | Number:21
 31 | Number:31
 41 | Number:41
 51 | Number:51
 61 | Number:61
 71 | Number:71
 81 | Number:81
 91 | Number:91
(10 rows)

UPDATE 10
 setval 
--------
     10
(1 row)

 id |   tekst   
----+-----------
  1 | Number:1
  2 | Number:11
  3 | Number:21
  4 | Number:31
  5 | Number:41
  6 | Number:51
  7 | Number:61
  8 | Number:71
  9 | Number:81
 10 | Number:91
(10 rows)

警告警告警告警告警告警告警告ACHTUNG:

キー値を変更することは、一般的にひどい考えです。絶対に避けてください。

于 2013-03-20T15:47:22.310 に答える