2013-04-01 124 views
14

我有一個表播放器和一個主鍵播放器ID是字符(7)。我已經在這個表中有一些記錄,並且還有一些其他表將playerID作爲外鍵,並且這些表也已經有一些記錄。更改主鍵自動增量

如何將playerID設置爲自動增加?在閱讀了一段時間後,我認爲我應該從一開始就這樣做,但由於我現在不能這樣做,反正我能做到嗎?

例如,當我運行這個

ALTER TABLE player ADD COLUMN key_column BIGSERIAL PRIMARY KEY; 

它返回一個錯誤:

ERROR: multiple primary keys for table "player" are not allowed 

,如果我刪除現有playerID,在引用它的其他表中的記錄也會被丟棄。

有沒有辦法將現有主鍵playerID「改變」爲自動增量?

回答

31

表我搞清楚同一DB-用戶:只需添加一個自動遞增默認值到playerID:

create sequence player_id_seq; 
alter table player alter playerid set default nextval('player_id_seq'); 
Select setval('player_id_seq', 2000051); --set to the highest current value of playerID 
1

我不認爲你可以有一個表中的2個主鍵,因爲playerID數據類型是字符(7)我不認爲你可以改變它自動增量。

所以我相信你必須刪除playerID上的主鍵約束,如果你想能夠添加一個新的主鍵。

既然你已經有數據在你的桌子上,並且你在其他桌子上使用playerID作爲外鍵,我會建議你複製你的桌子並在第二張桌子上測試這些變化以避免破壞你的數據。

但你嘗試這一切之前,請確保您正試圖使這種改變使用創建要更改

5
DROP SCHEMA tmp CASCADE; 
CREATE SCHEMA tmp ; 
SET search_path=tmp; 

    -- create som data to play with 
CREATE TABLE bagger 
     (player_id CHAR(6) 
     , tralala varchar 
     ); 

    -- populate the table 
INSERT INTO bagger(player_id,tralala) 
SELECT gs::text, 'zzz_' || gs::text 
FROM generate_series(1,10) gs 
     ; 

SELECT * FROM bagger; 

    -- 
    -- create the sequence, change the datatype and bind it to the sequence 
    -- 
CREATE SEQUENCE player_id_seq; 
ALTER TABLE bagger 
     ALTER COLUMN player_id TYPE INTEGER USING player_id::integer 
     , ALTER COLUMN player_id SET NOT NULL 
     , ALTER COLUMN player_id SET DEFAULT nextval('player_id_seq') 
     ; 
ALTER SEQUENCE player_id_seq 
     OWNED BY bagger.player_id 
     ; 
    -- 
    -- reset the sequence to containe the maximum occuring player_id in the table 
    -- 
SELECT setval('player_id_seq', mx.mx) 
FROM (SELECT MAX(player_id) AS mx FROM bagger) mx 
     ; 
SELECT * FROM bagger; 
\d bagger 

輸出:

DROP SCHEMA 
CREATE SCHEMA 
SET 
CREATE TABLE 
INSERT 0 10 
player_id | tralala 
-----------+--------- 
1   | zzz_1 
2   | zzz_2 
3   | zzz_3 
4   | zzz_4 
5   | zzz_5 
6   | zzz_6 
7   | zzz_7 
8   | zzz_8 
9   | zzz_9 
10  | zzz_10 
(10 rows) 

CREATE SEQUENCE 
ALTER TABLE 

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

player_id | tralala 
-----------+--------- 
     1 | zzz_1 
     2 | zzz_2 
     3 | zzz_3 
     4 | zzz_4 
     5 | zzz_5 
     6 | zzz_6 
     7 | zzz_7 
     8 | zzz_8 
     9 | zzz_9 
     10 | zzz_10 
(10 rows) 

           Table "tmp.bagger" 
    Column |  Type  |      Modifiers      
-----------+-------------------+----------------------------------------------------- 
player_id | integer   | not null default nextval('player_id_seq'::regclass) 
tralala | character varying |