С учетом следующей таблицы SQL (например, MySQL):
CREATE TABLE `table` (
`id` int(11) unsigned NOT NULL,
`lang` tinyint(3) unsigned NOT NULL,
`data` text NOT NULL,
PRIMARY KEY (`id`,`lang`)
) ENGINE=InnoDB
В этой таблице хранятся некоторые данные об объектах с идентификаторами id
и data
, которые можно записать на нескольких языках = lang
. Типичный пример использования этой таблицы: нам нужно получить data для некоторого объекта с некоторым id и языком lang = 1 или хотя бы lang = 5 или любой другой язык, если не найдено строк с lang = 1 или 5 для id = 1.
Другими словами, я хочу получить информацию об объекте с id = 1 на английском или, по крайней мере, на немецком языке, но если нет - любого другого языка будет достаточно.
Это довольно простой запрос:
SELECT * FROM `table` WHERE `id` = 1
ORDER BY
CASE WHEN `lang` = 1 THEN 1
WHEN `lang` = 2 THEN 2
ELSE 3
END ASC
LIMIT 1
Этот запрос довольно быстрый и использует только ПЕРВИЧНЫЙ ключ с сортировкой в памяти.
Вопросы появляются, когда мы хотим получить такие данные для нескольких объектов одним запросом. Единственное, о чем я могу думать, это что-то вроде:
SELECT id, (SUBQUERY TO GET DATA AS ABOVE WHERE id = tmp.id LIMIT 1) AS data
FROM (SUBQUERY TO SELECT ids) as tmp
Этот запрос выполнит свою работу, но выглядит и выглядит ужасно: /
И это первый вопрос: - это хороший и правильный способ делать такие вещи? Кто-нибудь знает лучший способ решения таких проблем?
Теперь давайте подумаем о высоконагруженных и действительно больших таблицах данных. Например, предположим, что мы дали 1 000 000 объектов с 5–15 языками для каждого. Это действительно огромная таблица для MySQL, поэтому мы разделим одну таблицу на несколько (скажем, 20 таблиц на нескольких серверах). Теперь у нас есть простая хеш-функция (например, id% N == 0), чтобы узнать, где хранятся данные для конкретного объекта.
Итак, вопрос № 2 : * Как сделать такие запросы по нескольким таблицам (даже в одной базе данных, от table_1 до table_5), если мы уже знаем, где находятся данные? * Я предполагаю, что этот вопрос можно ответить только после первого: (
Несколько других вопросов по этой теме : может быть, вся ситуация не так? Должны ли мы хранить такие данные другим способом? Или, может быть, есть другие, более эффективные способы сделать это?