2012-01-18 5 views
6

に条件付きの一意のインデックスを追加する方法:次の列で、私は<code>line_items</code>テーブルを持っているPostgreSQLの

product_id 
variant_id 

variant_idはNULLです。ここで

が条件です:

  • variant_idがNULLの場合、product_idは一意である必要があります。
  • variant_idに値がある場合、product_idvariant_idの組み合わせは一意である必要があります。

PostgreSQLで可能ですか?

答えて

20

(product_id, variant_id)UNIQUE multicolumn INDEXを作成します。

CREATE UNIQUE INDEX line_items_prod_id_var_id_idx 
ON line_items (product_id, variant_id); 

NULL値は同一とみなされていないので、しかし、これは(product_id, variant_id)ため(1, NULL)の複数のエントリを可能にします。あなたが(1,2)(1,3)(1, NULL)が、それらのどちらも二時間を入力することができます

CREATE UNIQUE INDEX line_items_prod_id_var_null_idx 
ON line_items (product_id) 
WHERE variant_id IS NULL; 

この方法:
はさらにpartial UNIQUE INDEXproduct_id上を作成し、その補うために。また、一方または両方の列の条件でクエリを高速化します。

このanswer on dba.SE私が最近書いたのは、あなたの問題に非常によく似ており、ほとんど直接的に当てはまります。

0

また、キーフィールドに式を使用することもできます。これは、あなたが質問したときには周りにはなかったかもしれませんが、今これを見て他の人に役立つ可能性があります。確かに

CREATE UNIQUE INDEX line_items_prod_id_var_id_idx 
ON line_items (product_id, (coalesce(variant_id, 0))); 

、これはあなたのvariant_id式を囲む括弧に注意してください。また1から開始し、自動インクリメントの整数であることを前提としています。ドキュメントごとに、それらが必要です。

http://www.postgresql.org/docs/9.3/static/sql-createindex.html

関連する問題