MySQL / INNER JOIN

INNER JOIN

INNER JOIN нь хоёр хүснэгтийн хоёуланд нь тохирох мөрүүдийг нэгтгэж буцаана. JOIN бол харилцааны өгөгдлийн сангийн хамгийн хүчирхэг хэрэгслүүдийн нэг.

JOIN-гүй асуудал

Захиалга харахад user_id=1 гэж харагдана — хэрэглэгчийн нэрийг мэдэхийн тулд тусдаа query хийх хэрэгтэй болно:

sql
SELECT * FROM orders;        -- user_id=1 харагдана
SELECT * FROM users WHERE id = 1;  -- нэрийг тусдаа татна

JOIN ашигласнаар нэг query-д хоёр хүснэгтийн мэдээллийг нэгтгэж авна.


INNER JOIN синтакс

sql
SELECT багана
FROM хүснэгт1
INNER JOIN хүснэгт2 ON хүснэгт1.багана = хүснэгт2.багана;

Жишээ — захиалга ба хэрэглэгч:

sql
SELECT
  orders.id         AS захиалга_id,
  users.name        AS хэрэглэгч,
  orders.quantity,
  orders.created_at
FROM orders
INNER JOIN users ON orders.user_id = users.id;
код
+------------+------------------+----------+---------------------+
| захиалга_id| хэрэглэгч        | quantity | created_at          |
+------------+------------------+----------+---------------------+
|          1 | Болд Батбаяр     |        1 | 2024-06-01 11:00:00 |
|          2 | Болд Батбаяр     |        2 | 2024-06-01 11:01:00 |
|          3 | Дорж Гантулга    |        1 | 2024-06-01 11:02:00 |
+------------+------------------+----------+---------------------+

INNER JOIN нь зөвхөн хоёр хүснэгтэд хоёуланд нь тохирох мөрүүдийг буцаана. orders.user_id-д тохирох users.id байхгүй захиалгууд үр дүнд ороход орохгүй.


Table alias

Хүснэгтийн нэрийг товчилж бичих нь уншихад хялбар болгоно:

sql
SELECT
  o.id        AS захиалга_id,
  u.name      AS хэрэглэгч,
  p.name      AS бараа,
  o.quantity,
  p.price,
  p.price * o.quantity AS нийт_үнэ
FROM orders AS o
INNER JOIN users    AS u ON o.user_id    = u.id
INNER JOIN products AS p ON o.product_id = p.id;
код
+------------+------------------+--------------------+----------+----------+----------+
| захиалга_id| хэрэглэгч        | бараа              | quantity | price    | нийт_үнэ |
+------------+------------------+--------------------+----------+----------+----------+
|          1 | Болд Батбаяр     | Bluetooth чихэвч   |        1 | 29900.00 | 29900.00 |
|          2 | Болд Батбаяр     | Цэнэглэгч кабель   |        2 |  1990.00 |  3980.00 |
|          3 | Дорж Гантулга    | Утасны дэр         |        1 |  4990.00 |  4990.00 |
|          4 | Мөнх Эрдэнэ      | Ухаалаг цаг        |        1 | 89900.00 | 89900.00 |
+------------+------------------+--------------------+----------+----------+----------+

AS түлхүүр үгийг орхиж болно: FROM orders o → ижил утга.


Олон хүснэгт JOIN хийх

Хэдэн ч хүснэгт нэмж болно:

sql
SELECT
  o.id                     AS захиалга,
  u.name                   AS хэрэглэгч,
  u.email,
  p.name                   AS бараа,
  p.price,
  o.quantity,
  p.price * o.quantity     AS нийт,
  o.created_at
FROM orders        AS o
INNER JOIN users    AS u ON o.user_id    = u.id
INNER JOIN products AS p ON o.product_id = p.id
WHERE o.created_at >= '2024-01-01'
ORDER BY o.created_at DESC
LIMIT 20;

WHERE + JOIN

JOIN-тэй query-д WHERE хэрэглэх үед аль хүснэгтийн баганыг заахыг тодорхой бичнэ:

sql
-- Болд-ийн захиалгуудыг харах
SELECT o.id, p.name, o.quantity
FROM orders AS o
INNER JOIN users    AS u ON o.user_id    = u.id
INNER JOIN products AS p ON o.product_id = p.id
WHERE u.name = 'Болд Батбаяр';
sql
-- 10,000-аас дээш үнэтэй захиалгууд
SELECT u.name, p.name AS bараа, p.price
FROM orders AS o
INNER JOIN users    AS u ON o.user_id    = u.id
INNER JOIN products AS p ON o.product_id = p.id
WHERE p.price > 10000
ORDER BY p.price DESC;

JOIN vs Subquery

Ижил үр дүнг JOIN болон subquery хоёуланг ашиглан бичиж болно:

sql
-- JOIN ашиглан
SELECT u.name, COUNT(o.id) AS захиалгын_тоо
FROM users AS u
INNER JOIN orders AS o ON u.id = o.user_id
GROUP BY u.id, u.name;

-- Subquery ашиглан
SELECT name,
  (SELECT COUNT(*) FROM orders WHERE user_id = u.id) AS захиалгын_тоо
FROM users AS u;

Хэзээ JOIN дээр:

  • Нэгдсэн өгөгдлийг (олон баганыг) харуулах шаардлагатай үед
  • Нэг хүснэгтээс олон хүснэгт рүү холбоход
  • GROUP BY + aggregate функцтэй хамт

Хэзээ Subquery дээр:

  • Дотор query нэг утга буцаах үед
  • IN (SELECT ...) шалгалт хийх үед
  • Query-г ойлгоход хялбар болгохын тулд хэсэгчлэн бичих үед

Ерөнхийдөө JOIN нь гүйцэтгэлийн хувьд давуу — MySQL query optimizer JOIN-ийг илүү сайн оновчилдог.


Self JOIN — хүснэгтийг өөрөөр JOIN хийх

Нэг хүснэгтийн мөрүүдийг бие биетэйгээ харьцуулах:

sql
-- Ажилчид ба тэдний менежер (нэг хүснэгтэд)
CREATE TABLE employees (
  id         INT PRIMARY KEY,
  name       VARCHAR(100),
  manager_id INT  -- өөрийн хүснэгтийн id-г заана
);

SELECT
  e.name    AS ажилтан,
  m.name    AS менежер
FROM employees AS e
INNER JOIN employees AS m ON e.manager_id = m.id;

Дараагийн хичээлд:

LEFT JOIN ба RIGHT JOIN — тохирохгүй мөрүүдийг хэрхэн хадгалах, NULL утгуудтай ажиллах аргуудыг үзнэ.