Ответ
FULL OUTER JOIN (в некоторых СУБД просто FULL JOIN) — это тип объединения таблиц, который возвращает все строки из обеих таблиц.
Принцип работы:
- Возвращаются все строки, для которых выполняется условие объединения (как в
INNER JOIN). - Возвращаются все строки из левой таблицы, для которых не нашлось совпадений в правой (как в
LEFT JOIN), при этом столбцы правой таблицы заполняютсяNULL. - Возвращаются все строки из правой таблицы, для которых не нашлось совпадений в левой (как в
RIGHT JOIN), при этом столбцы левой таблицы заполняютсяNULL.
Пример SQL-запроса:
SELECT c.name, o.order_id
FROM customers c
FULL OUTER JOIN orders o ON c.id = o.customer_id;
Результат будет содержать:
- Клиентов, у которых есть заказы.
- Клиентов, у которых нет заказов (поле
order_idбудетNULL). - Заказы, у которых по какой-то причине нет связанного клиента (поле
nameбудетNULL).
Применение в Go:
В Go вы просто пишете SQL-запрос как строку и выполняете его с помощью пакета database/sql. Go не интерпретирует сам SQL, а отправляет его в СУБД. Ключевой момент — правильная обработка NULL значений, которые вернет запрос. Для этого в Go используются специальные типы из пакета database/sql, такие как sql.NullString, sql.NullInt64 и т.д.
var customerName sql.NullString
var orderID sql.NullInt64
err := row.Scan(&customerName, &orderID)
// ...
if customerName.Valid {
// Используем customerName.String
}
// Если !customerName.Valid, значит, в базе было NULL Ответ 18+ 🔞
Давай разберём эту штуку, FULL OUTER JOIN, а то народ иногда в ступор впадает, как будто им хуй с горы показали.
Представь, что у тебя есть две таблицы. Одна — про клиентов, другая — про заказы. И вот ты такой царь-батюшка, хочешь увидеть ВСЁ И СРАЗУ. Всех клиентов, все заказы, и чтобы те, кто совпали, были вместе, а кто нет — так и висели по отдельности, как манда с ушами.
Вот как это работает, ёпта:
- Совпадения (как INNER JOIN): Берутся все парочки, где клиенту в заказе повезло и он нашёлся. Красота.
- Левые сироты (как LEFT JOIN): Берутся все клиенты, которые такие одинокие, что заказа у них нихуя нет. На месте заказа будет пустота,
NULL. - Правые сироты (как RIGHT JOIN): Берутся все заказы-подкидыши, которые непонятно от какого клиента припёрлись. На месте имени клиента — та же пустота,
NULL.
Вот тебе пример запроса, смотри:
SELECT c.name, o.order_id
FROM customers c
FULL OUTER JOIN orders o ON c.id = o.customer_id;
Что в итоге вылезет? Да всё, блядь!
- Вася (клиент) и его заказ №5.
- Петя (клиент), который нихуя не заказывал, но мы его всё равно видим. Рядом с
order_id—NULL. - Заказ №42, который есть, а клиент на него записан какой-то левый, которого у нас в базе нет. Рядом с
name—NULL.
А как это в Go применить?
А вот тут внимание, волнение ебать! Go сам SQL не жуёт, он его тупо отправляет в базу. Вся магия — в обработке ответа. Потому что эти самые NULL значения обычными string или int не прочитать, пидарас шерстяной! Надо использовать специальные обёртки.
Смотри, как это выглядит:
var customerName sql.NullString
var orderID sql.NullInt64
err := row.Scan(&customerName, &orderID)
// ...
if customerName.Valid {
// Всё ок, имя есть, работаем с customerName.String
} else {
// А тут customerName.Valid == false. Значит, в базе был NULL. Клиента нет, заказ-сирота.
}
Вот и весь секрет. FULL OUTER JOIN — это когда тебе похуй на логику связей, ты хочешь всю картину, со всеми дырками и нестыковками. Как жизнь, только в SQL.