Что может быть лучше, чем собирать идентификаторы из результатов GROUP_CONCAT и выполнять второй запрос для получения данных «один ко многим»?

Часто мне приходится писать SQL-запросы по следующей схеме:

SELECT A.*, GROUP_CONCAT(B.b_id SEPARATOR ';') b_list
FROM A
LEFT JOIN B ON B.a_id = A.a_id
GROUP BY A.a_id

Существует отношение один ко многим; один A может иметь несколько Bs.
Теперь я хочу перечислить все As и для каждого из них вывести список всех B, назначенных ему одновременно.

Моя проблема в том, что я хочу также отобразить все столбцы B, и для их получения мне нужно выполнить дополнительный запрос, извлекающий данные для всех b_ids, которые появляются в одном из b_lists в наборе результатов. Чтобы добиться этого, я дважды перебирал набор результатов: сначала я собираю все необходимые b_ids, после чего запускаю второй запрос SELECT * FROM B WHERE b_id IN(...collected b_ids...) и сохраните результат в ассоциативный массив с ключом b_id. Затем я могу легко перебрать набор результатов снова и распечатать данные, обратившись к моему массиву, содержащему столбцы B.

Есть ли лучшая практика для достижения этого? Конечно, я мог бы объединить все столбцы в первом запросе без GROUP BY, но в целом мои таблицы A и B довольно сложны, и я хочу избежать избыточности, которая вызвана тем, что столбцы A «копируются» для каждого B.

0

Решение

Вы можете поместить столбцы, которые вы хотите в group_concat():

SELECT A.*, GROUP_CONCAT(CONCAT_WS(',', '(', B.b_id, B.col1, b.col2, ')') SEPARATOR ';') as b_list
FROM A LEFT JOIN
B
ON B.a_id = A.a_id
GROUP BY A.a_id;

Это даст вам разделенные запятыми значения в скобках, разделенные точкой с запятой.

1

Другие решения

Других решений пока нет …

По вопросам рекламы [email protected]