😽

SQLにおけるエイリアスと可読性について考える

に公開

こんにちは。そやまです。
データ分析に欠かせないスキルの1つであるSQL。
そんなSQLを書くときに、エイリアスをどう付けるかは意外と人によって流派の分かれるポイントだと思います。
このブログでは、SQLのエイリアスについて個人的見解をまとめたものをお話させていただきます。

今回は、例として以下のSQLを題材に考えていきます。

SELECT
  customers.customer_name,
  subscriptions.plan_name,
  SUM(payment_transactions.amount) AS total_paid_amount
FROM payment_transactions
INNER JOIN subscriptions
  USING (subscription_id)
INNER JOIN customers
  USING (customer_id)
GROUP BY
  customers.customer_name,
  subscriptions.plan_name;

よく見かけるエイリアスのパターン

経験上、以下のようなパターンを目にしてきました。

  • t1, t2 のように Tableの頭文字 + 連番
SELECT
  t3.customer_name,
  t2.plan_name,
  SUM(t1.amount) AS total_paid_amount
FROM payment_transactions AS t1
INNER JOIN subscriptions AS t2
  USING (subscription_id)
INNER JOIN customers AS t3
  USING (customer_id)
GROUP BY
  t3.customer_name,
  t2.plan_name;
  • a, b, c のようなアルファベット順
SELECT
  c.customer_name,
  b.plan_name,
  SUM(a.amount) AS total_paid_amount
FROM payment_transactions AS a
INNER JOIN subscriptions AS b
  USING (subscription_id)
INNER JOIN customers AS c
  USING (customer_id)
GROUP BY
  c.customer_name,
  b.plan_name;
  • テーブル名のイニシャルを取るパターン
SELECT
  c.customer_name,
  s.plan_name,
  SUM(pt.amount) AS total_paid_amount
FROM payment_transactions AS pt
INNER JOIN subscriptions AS s
  USING (subscription_id)
INNER JOIN customers AS c
  USING (customer_id)
GROUP BY
  c.customer_name,
  s.plan_name;
  • 1単語で表現するパターン
SELECT
  customer.customer_name,
  subscription.plan_name,
  SUM(payment.amount) AS total_paid_amount
FROM payment_transactions AS payment
INNER JOIN subscriptions AS subscription
  USING (subscription_id)
INNER JOIN customers AS customer
  USING (customer_id)
GROUP BY
  customer.customer_name,
  subscription.plan_name;

ここまでに読者の皆さまが日頃採用されているパターンはありましたでしょうか?
この程度の短いコードであればどれを採用しても大差ないかもしれません。
しかし、テーブル数が多く、集計も複雑な場合はどうでしょうか?
どれも「間違い」ではありませんが、読み手がどれだけ負荷なく理解できるかという点では差が出ると感じています。

可読性を重視した個人的な使い分け

私自身は、以下のような基準でエイリアスを使い分けています。

テーブル名が非常に長いとき

  • 1単語のエイリアスを付ける
SELECT
  customer.customer_name,
  subscription.plan_name,
  SUM(payment.amount) AS total_paid_amount
FROM finance_payment_settlement_transaction_events AS payment
INNER JOIN subscription_contract_registry_master AS subscription
  USING (subscription_id)
INNER JOIN crm_customer_profile_dimension_snapshots AS customer
  USING (customer_id)
GROUP BY
  customer.customer_name,
  subscription.plan_name;

そのテーブルの性格をよく表す1単語をエイリアスにします。
この際、単語の選択を誤ると逆に混乱を招く原因ともなり得るので、慎重に選ぶことが重要です。

テーブル名がさほど長くないとき

  • あえてエイリアスを使わず、テーブル名をそのまま採用する
SELECT
  customer_profiles.customer_name,
  subscription_contracts.plan_name,
  SUM(payment_transactions.amount) AS total_paid_amount
FROM payment_transactions
INNER JOIN subscription_contracts
  USING (subscription_id)
INNER JOIN customer_profiles
  USING (customer_id)
GROUP BY
  customer_profiles.customer_name,
  subscription_contracts.plan_name;

エイリアスを付けると記述量は減りますが、その分「このエイリアスはどのテーブルだっけ?」という認識コストが発生します。
それを避けるためにもエイリアスを使用しないことが多いです。
場合にもよりますが、2単語までであればさほど長くないと判断します。

個人で検証をするとき

  • イニシャルを取る
SELECT
  cp.customer_name,
  sc.plan_name,
  SUM(pt.amount) AS total_paid_amount
FROM payment_transactions AS pt
INNER JOIN subscription_contracts AS sc
  USING (subscription_id)
INNER JOIN customer_profiles AS cp
  USING (customer_id)
GROUP BY
  cp.customer_name,
  sc.plan_name;

これは「素早く書いて、素早く捨てるSQL」であることが前提です。
チームで共有されるコードや、将来参照される可能性のあるSQLでは採用しません。

なぜ可読性を重視するのか

理由はシンプルで、自分以外が読んだときの負担を減らしたいからです。
どのテーブルのカラムを参照しているのか
JOINの関係性はどうなっているのか
これらを読み手が頭の中で変換する必要が少ないほど、SQLは「読みやすい」と言えると思っています。
エイリアスは便利な機能ですが、
「短くするため」ではなく「読みやすくするため」に使うのがよいのではないでしょうか。

名は体を表すとはよく言ったものですが、テーブル名は意味があってその形になっています。
長くて億劫に感じる名前にも、他テーブルとの混同を避けるための工夫が詰まっています。
エイリアスを何にするのか迷った際には、思い切ってエイリアスを付けないという選択をとるのがよいかもしれません。

おわりに

SQLのエイリアスに正解はありません。
ですが、可読性という軸を持って選択しているかどうかは、コードの質に大きく影響すると考えています。
自分のSQLを、未来の自分やチームメンバーが読んだときにどう感じるか。
その視点を持つだけでも、エイリアスの付け方は変わってくるのではないでしょうか。

truestarテックブログ

Discussion