Mysql. Связанные таблицы. Ниче не пойму.
1.
SD (13.03.2010 / 22:40)
1) Допустим, есть три таблицы. Юзеры(поля ид, имя и.тд.), Команда(в ней поля ид, ид юзера, ид группы), Группы(ид, название, и.т.д).
Задача - зная ид юзера вывести название группы.
Можно сначала узнать ид группы, потом название, двумя запросами. Но если идов таких 10 или более, получается куча запросов и большое время генерации. Как это всё в один впихнуть? Чтобы, например, вывести всех юзеров(не все есть в таблице команда) и рядом с ними вывести название группы.
2) допустим - гостевая. Та же ситуация, что и выше. Куча записей и надо вывести рядом с ником названия групп.
И, объясните, кто-нибудь про связанные таблицы вообще. Первичный ключ итд. Или линк подкиньте. Заранее спасибо.
2.
chiper (13.03.2010 / 22:45)
1.
Dark Person, как я понял, то тебе надо делать запрос и выводить в цикле этот айди. а с помощью него в цикле делать запрос, и уже делать вывод. ну я лично так делаю
3.
SD (13.03.2010 / 22:50)
Дак а ты представь, если будет на странице 20 записей. 1 запрос на иды юзеров+20х1 запрос на узнавание ида группы+20х1 запрос на узнавание имени команды. Итого 41 запрос к бд. Нехило, да? Вот мне интересно, можно ли это в 1 запрос впихнуть, чтобы поле с именем из другой таблицы добавилось в результат запроса. Я так понимаю, надо юзать join, но вот вкурить его не могу..
4.
Олег (13.03.2010 / 23:26)
SELECT users.`*`, group.name FROM users
LEFT JOIN group ON group.id = users.group_id
WHERE id_user = $id_user
ORDER BY users.id_user
5.
SD (14.03.2010 / 13:11)
Сам разобрался. Мож кому пригодится:
SELECT users.*, groups.title FROM users LEFT JOIN command ON command.user=users.id LEFT JOIN groups ON groups.id = command.status
Время запроса - 0.0050 сек..
В отличие от 0.0015+0.0016х4+0.0016х4=0.0143 сек.
З.ы. И это таблице юзеров было только 4 записи;)
6.
Azzido (15.03.2010 / 06:27)
можно было впринципе с внешним ключом подумать
7.
DmitryDick (15.03.2010 / 06:39)
автор, ты бы структуру таблиц сменил, таблица, хранящая "Команда(в ней поля ид, ид юзера, ид группы)" и не нужна, просто добавляешь поле `group_id` в таблицу с юзерами и
select `users`.*, `groups`.`title`
from `users`
left join `groups` on `groups`.`id`=`users`.`group_id`
8.
Max (19.03.2010 / 09:10)
А индексы тут помогут?
9.
DmitryDick (19.03.2010 / 17:34)
8, т.е.?
10.
Валерий (13.06.2010 / 00:09)
Aligan (14.03.10 / 04:26)
SELECT users.`*`, group.name FROM users
LEFT JOIN group ON group.id = users.group_id
WHERE id_user = $id_user
ORDER BY users.id_user
Вот я ниразу не пользовался командой JOIN в запросах.. Я бы написал так:
SELECT users.name AS uname, group.name AS gname
FROM users,group
WHERE group.id=users.group_id
AND users.id='$id_user'
ORDER BY users.id
Вот скажите, мой запрос чем то хуже предыдущего? Или они одинаковы?
11.
Олег (13.06.2010 / 02:43)
phpcoder, потому что соединить и объединить это разные вещи. Перечисление в секции FROM вообще плохой тон. в твоем запросе нельзя использовать ни левое ни правое объединение, только внутренние.
Если хочешь больше критики запости запрос на сайте gavnokod.ru))))
12.
Валерий (13.06.2010 / 14:13)
Опа, а куда 4 поста стерли? Aligan ну ты в чем то прав.. Во всяком случае я разобрался где и когда надо join ставить. Хотя мне это никогда не надо было.
Ps. Есть здесь нормальные кодеры.. Но большинство говнокодеры
13.
aAligan (13.06.2010 / 15:11)
Да гавнокодеры есть везде, в том числе и на самом говнокоде. Также утверждение telnet'а о том что парсер будет переносить запрос из ON в WHERE это полный бред равный нулю. Здесь вопрос больше дизайна и юзабилия кода касается. Я считаю что использование JOIN намного читабильнее и правильне, интуитивно понятнее. Я не представляю как нужно будет извращаться с запросомс "запятой", когда нужно будет объединить более 2 таблиц, а если еще типы объединения разные. Я пишу запросы в приложениях, где помиомо ещенужно обращаться к справочникам для создания сложных отчетов. Например вот один не самый сложный, но очень удачный пример где человек знающий операции JOIN легко может понять суть запроса
$sql = "
SELECT
{$PRE}lab_type_research.name,
{$PRE}lab_markers.name_marker,
{$PRE}lpu.name_lpu,
{$PRE}lpu.lpu_id,
{$PRE}lab_markers_values.id_type_research,
{$PRE}lab_markers_values.marker_id,
{$PRE}lab_markers_values.`values` AS status,
count(*) AS col
FROM
{$PRE}lab_markers_values
INNER JOIN
{$PRE}lab_analyses ON {$PRE}lab_analyses.number_research = {$PRE}lab_markers_values.number_research
AND {$PRE}lab_analyses.id_type_research = {$PRE}lab_markers_values.id_type_research
AND {$PRE}lab_analyses.data BETWEEN '{$data_first}' and '{$data_second}'
{$where_lpu}
INNER JOIN
{$PRE}lab_markers ON {$PRE}lab_markers_values.marker_id = {$PRE}lab_markers.marker_id
INNER JOIN
{$PRE}lab_type_research ON {$PRE}lab_type_research.research_id = {$PRE}lab_markers_values.id_type_research
INNER JOIN
{$PRE}lpu ON {$PRE}lpu.lpu_id = {$PRE}lab_analyses.lpu_id
GROUP BY
{$PRE}lab_analyses.lpu_id,
{$PRE}lab_markers_values.id_type_research,
{$PRE}lab_markers_values.marker_id,
{$PRE}lab_markers_values.`values`
ORDER BY
{$PRE}lpu.lpu_id";
URL:
https://visavi.net/topics/6959