0
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

More than 3 years have passed since last update.

HAVING句でデータの歯抜けを探す方法を見ながら、集合思考言語と手続き型言語の違いを考える(1/2)

Last updated at Posted at 2021-09-30

はじめに

HAVING句でデータの歯抜けを探す方法を見ながら、集合思考言語と手続き型言語の違いを考えてみます。

Schema (MySQL v8.0)

CREATE TABLE members (
  id INT NOT NULL PRIMARY KEY auto_increment,
  name TEXT
);

INSERT INTO members VALUES
    (1, 'brown'),
    (2, 'rally'),
    (3, 'boggie'),
    (5, 'tashiro'),
    (6, 'yamada'),
    (8, 'takeda');

Result

id name
1 brown
2 rally
3 boggie
5 tashiro
6 yamada
8 takeda

このデータの歯抜けをどう探しますか?

仮に、このテーブルがファイルで、手続き型言語を使って調べるなら...

  • ソートする
  • ソート順にループさせて、1行づつ次の行と比較

ファイルのレコードは順序を持ち、それを扱うためのプログラミング言語もソートを行えます。

一方、テーブルの行は順序を持ちませんし、SQLもソートの演算子を持っていません。

ORDER BY 句はSQLの演算子ではなくカーソル定義の一部です。

ORDER BY は、結果を表示する目的には便利だが、それ自体はリレーショナル演算子ではない。

引用👇(15のページに記載)

SQLではどう表現するか

複数行を1つにまとめて集合として扱います。

query

SELECT '歯抜けあり' AS gap
FROM members
HAVING COUNT(*) <> MAX(id)

<>は、jsでいう!==で、等しくないという意味です。

results

gap
歯抜けあり

このクエリは、1行返れば「歯抜けあり」が返るが何も返らなければ連番であるということになります。

図解するとこういう感じです。

IMG_72EFC2BE915B-1.jpeg

つまり、一方の集合は他方の写像であることをテストしていることになります。

image.png

上記のクエリは、歯抜けが存在する場合、絶対不一致になりますね。

HAVINGはGROUP BY と併用しなければいけないわけでは無い

現在の標準SQLでは、HAVING句を単独で使えるそうです。

ただし、SELECT句で元テーブルの列を参照できなくなるので、上記SQLのように、定数を返すようにするか、以下のように集約関数を使う必要があります。

SELECT SUM(*) FROM ...

本日は、以上です。

参照

105 - 109p

アウトプット100本ノック実施中

0
0
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
0
0

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?