私が探しているのは、既存のテーブルに制約 (一意など) を追加し、既存のデータに対して検証し、制約を削除するときに観察されるような動作です。制約をテーブルに永続化させたくありません。それを表現し、既存のデータで検証してから先に進みます (またはチェック失敗の例外を発生させます)。Postgresql (9.2) は、このようなことを直接行う方法をサポートしていますか?
質問する
306 次
3 に答える
2
制約を作成します。
alter table t
add constraint the_pk primary key (user_id);
NOTICE: ALTER TABLE / ADD PRIMARY KEY will create implicit index "the_pk" for table "t"
ERROR: could not create unique index "the_pk"
DETAIL: Key (user_id)=(1) is duplicated.
エラーがない場合はドロップします。
alter table t
drop constraint the_pk;
しばらく保持したくない場合は、トランザクション内で実行します。
begin;
alter table t
add constraint the_pk primary key (user_id);
満足したら、トランザクションをロールバックします。
rollback;
于 2013-06-07T16:10:45.597 に答える
1
IF EXISTS
plpgsql では、この目的のために一般的によりシンプルで高速です。
DO
$$
BEGIN
IF EXISTS (SELECT 1 FROM tbl GROUP BY tbl_id HAVING count(*) > 1) THEN
RAISE EXCEPTION 'Duplicate "tbl_id" in table "tbl"!';
END IF;
END
$$ LANGUAGE plpgsql;
于 2013-06-08T18:49:45.367 に答える
1
設定:
CREATE TABLE testu ( id integer );
INSERT INTO testu SELECT generate_series(1,100);
INSERT INTO testu VALUES (1),(10),(20);
問題のある可能性のある行を見つけるためのデモ クエリ:
regress=> select id, count(id) FROM testu GROUP BY id HAVING count(id) > 1;
id | count
----+-------
20 | 2
1 | 2
10 | 2
(3 rows)
DO
ブロックでラップします。
DO
$$
BEGIN
PERFORM id FROM testu GROUP BY id HAVING count(id) > 1 LIMIT 1;
IF FOUND THEN
RAISE EXCEPTION 'One or more duplicate IDs in table testu';
END IF;
END;
$$ LANGUAGE plpgsql;
衝突する個々の ID を報告したい場合は、クエリの結果から文字列を作成したり、結果をループしてNOTICE
s を上げたりすることでそれを行うことができます。多くのオプションがあります。PL/PgSQL ドキュメントを使用して、読者であるあなたに演習として残します。
于 2013-06-08T02:42:46.287 に答える