受講料が最大70%OFF 受講料が最大70%OFF

SQLで必ず指定する”UNIQUE”という制約ですが、皆さんはこの制約についてきちんと理解していますか?

UNIQUE制約は当たり前のように設定しているけど、何となく漠然とした理解程度でしかないという方もいると思います。

そこで今回の記事ではこの「UNIQUE制約」について、正しい使い方が出来るように解説していきたいと思います。

UNIQUE制約とは

該当カラムにUNIQUE制約に設定すると、設定されたカラムに対しては重複した値を設定することが不可能となります。

これについては、MicrosoftのSQLドキュメントでも次のように記述されています。

SQL Server 2019 (15.x) では、 SQL Server Management Studio または Transact-SQL を使用して UNIQUE 制約を作成し、主キー以外の特定の列に重複した値が入力されないようにします。 UNIQUE 制約を作成すると、対応する一意なインデックスが自動的に作成されます。

主キー(PRIMARY)・一意キー(UNIQUE)とユニークインデックスの違い

混同されがちな項目ですが、一意キー(UNIQUE)はテーブルに付与する制約です。

言い換えると、テーブルに格納されるレコードに対して制限を付けるだけなので、当然「オブジェクト」ではありません。

記述方式に関しても「ALTER TABLE ~」とし、テーブルオブジェクトに対して付与する形となります。

これとは別にもう一つ「主キー(PRIMARY)」というものがありますが、こちらも「一意キー(UNIQUE)」と同じ「制約」となります。

では主キー(PRIMARY)と一意キー(UNIQUE)の違いは?という部分についてですが、以下のような違いがあります。

またもう一つ、UNIQUEと似たような名前の「ユニークインデックス」というものがありますが、このユニークインデックスはオブジェクトとなります。

ユニークインデックスを作成するには「CREATE UNIQUE INDEX ~」とします。

一意キー(UNIQUE)とユニークインデックスについてはよく間違った解釈がされてしまうので、しっかりと違いについて把握しておきましょう。

ポテパンダの一言メモ

主キー(PRIMARY)や一意キー(UNIQUE)は、作成と同時にユニークインデックスも作成されます。

これは主キー(PRIMARY)や一意キー(UNIQUE)が重複チェックを行う際に、ユニークインデックスを使ってチェックを行っているためです。

ターミナルでUNIQUEを設定する方法

それではターミナルでUNIQUE制約を設定する方法について解説していきましょう。

まず最初に基本構文の記述についてです。

UNIQUE制約を設定するためには、次のように記述します。

CREATE TABLE テーブル名([[カラム名] UNIQUE], [カラム名], ...);

このように、設定したいカラム名に続けて”半角スペース + UNIQUE”記述するだけの簡単な様式になっています。

念のため、実際のコードで見てみましょう。

まずサンプルとして使用するデータベースとテーブルおよびカラムを作成します。

1> USE smaple_db
2> CREATE TABLE sample_table(
3> no integer UNIQUE,
4> name varchar(MAX),
5> age integer
6> );
7> SELECT name FROM sysobjects WHERE xtype = 'U'
8> GO

name
-----------------------------------------------
sample_table

1> SELECT * FROM sample_table
2> GO

no          name        age
----------- ----------- ----------- 

これで準備は整いました。

それではデータを追加してみます。

1> INSERT INTO sample_table VALUES(1, 'Gordon', 28);
2> INSERT INTO sample_table VALUES(2, 'Smith', 20);
3> INSERT INTO sample_table VALUES(3, 'Williams', 30);
4> GO

(1 行処理されました)
(1 行処理されました)
(1 行処理されました)

単純にデータを追加しただけなので、問題なく追加できました。

それでは今度はUNIQUE指定したカラムに同じ数字を入れてみます。

1> INSERT INTO sample_table VALUES(1, 'Brown', 40);
2> GO
メッセージ 2627、レベル 14、状態 1、サーバー DESKTOP-T3J7G2K\SQLEXPRESS、行 1
制約 'UQ__sample_t__3213D0814B10138F' の UNIQUE KEY 違反。オブジェクト 'dbo.sample_table' には重複するキーを挿入できません。重複するキーの値は (1) です。
ステートメントは終了されました。

UNIQUE制約が設定されているため、このようにエラーが返ってくることが確認できます。

なおUNIQUE制約を設定していた場合でも、NULL値は重複して格納できてしまうため、注意しましょう。

組み合わせカラムにUNIQUE制約を適用する方法

ここまではUNIQUEの基本的な使い方としてカラム単体に適用させる方法について解説しましたが、UNIQUEは複数のカラムを組み合わせたものに対しても設定が可能です。

こういったケースでは次のように記述します。

CREATE TABLE テーブル名([カラム名], [カラム名], ...,
UNIQUE([カラム名1], [カラム名2], ...));

この記述方法でUNIQUE制約を設定した場合、UNIQUE制約に記述した全てのカラムの値が同じ組み合わせだった場合にのみ重複不可となります。

逆にカラムの値の組み合わせを同一にしなければ、それぞれのカラムの値を重複させてもエラーとはなりません。

それではこちらも実際にコードで確認してみましょう。

1> CREATE TABLE sample_table(
2>      no integer,
3>      name varchar(30),
4>      age integer,
5>      UNIQUE(no, name)
6> );
7> GO

8> SELECT name FROM sysobjects WHERE xtype = 'U'
9> GO

name
--------------------------------------------------------------------------------------------------------------------------------
sample_table

(1 行処理されました)

10> SELECT * FROM sample_table
11> GO

no          name                           age
----------- ------------------------------ -----------

12> INSERT INTO sample_table VALUES(1, 'Gordon', 28);
13> INSERT INTO sample_table VALUES(1, 'Smith', 20);
14> INSERT INTO sample_table VALUES(2, 'Smith', 20);
15> GO

(1 行処理されました)
(1 行処理されました)
(1 行処理されました)

16> INSERT INTO sample_table VALUES(2, 'Smith', 28);
17> GO

メッセージ 2627、レベル 14、状態 1、サーバー DESKTOP-T3J7G2K\SQLEXPRESS、行 1
制約 'UQ__sample_t__853DC2704E79437F' の UNIQUE KEY 違反。オブジェクト 'dbo.sample_table' には重複するキーを挿入できません。重複するキーの値は (2, Smith) です。
ステートメントは終了されました。

1行~6行は上の構文に則った記述となっています。

まず見ていただきたいのは、24行~26行の3行です。

今回のケースではUNIQUE制約に「no」と「name」を設定していますが、24行~25行では”no”の値を、25行~26行では”name”の値を敢えて重複させています。

しかしこのINSERT文を実行すると、エラーが返ってくることなく実行されていることが確認できました。

では次は33行目を見てみましょう。

33行目では、既に26行目で登録されている内容の年齢だけを変更してINSERTをかけています。

このINSERTを実行した結果が36行目~となるわけですが、エラーメッセージが返ってきていることが確認できます。

内容を見てみても、37行目に「重複するキーの値は(2, Smith)です。」としっかり記述されています。

このように、UNIQUE制約は記述方法によって異なる動作となりますので、しっかりと違いを把握しておきましょう。

まとめ

いかがでしたか?

今回はUNIQUE制約の記述方法と違いについて解説してみました。

ターミナルから直接設定する機会は比較的少ないと思いますが、こういった方法を知っておけばIDE(統合開発環境)が何らかの理由で使用できない場合でも対応できます。

またSQLはターミナルを使用することで操作が楽になるケースもあるため、学習時には出来るだけターミナルの操作にも慣れておいた方が良いでしょう。

エンジニアになりたい人に選ばれるプログラミングスクール「ポテパンキャンプ 」

ポテパンキャンプは卒業生の多くがWebエンジニアとして活躍している実践型プログラミングスクールです。 1000名以上が受講しており、その多くが上場企業、ベンチャー企業のWebエンジニアとして活躍しています。

基礎的な学習だけで満足せず、実際にプログラミングを覚えて実践で使えるレベルまで学習したいという方に人気です。 プログラミングを学習し実践で使うには様々な要素が必要です。

それがマルっと詰まっているポテパンキャンプでプログラミングを学習してみませんか?

卒業生の多くがWebエンジニアとして活躍

卒業生の多くがWeb企業で活躍しております。
実践的なカリキュラムをこなしているからこそ現場でも戦力となっております。
活躍する卒業生のインタビューもございますので是非御覧ください。

経験豊富なエンジニア陣が直接指導

実践的なカリキュラムと経験豊富なエンジニアが直接指導にあたります。
有名企業のエンジニアも多数在籍し品質高いWebアプリケーションを作れるようサポートします。

満足度高くコスパの高いプログラミングスクール「ポテパンキャンプ」

運営する株式会社ポテパンは10,000人以上のエンジニアのキャリアサポートを行ってきております。
そのノウハウを活かして実践的なカリキュラムを随時アップデートしております。

代表の宮崎もプログラミングを覚えサイトを作りポテパンを創業しました。
本気でプログラミングを身につけたいという方にコスパ良く受講していただきたいと思っておりますので、気になる方はぜひスクール詳細をのぞいてくださいませ。