2015-02-12 2 views
1

У меня есть 2 стола. Один - Agent, а другой - Agent_Contact. Таблица Agent_Contact должна содержать контактную информацию Agent.Извлечь только одну запись из ОДНО-МНОГО отношений

Отношения с Agent к Agent_Contact является One-To-Many, который означает Agent может иметь много Agent_Contacts

Agent_Contact держит Foreign Key из Agent.

Может быть Agents, у кого нет Agent_Contact.

Теперь, пожалуйста, ознакомьтесь с нижеследующим кодом.

SELECT Agent.*, 
Agent_Contact.* 
FROM Agent 
LEFT JOIN Agent_Contact ON Agent.idAgent = Agent_Contact.idAgent 

Теперь это возвращает все Agents с их Agent_Contact с (если они есть). Однако представьте себе, что один Agent получил 15 Agent_Contact s, после чего он вернется 15 строк.

Это не то, что я хочу. Один раз Agent_Contact за один Agent достаточно. Но как я могу изменить вышеупомянутый запрос sql для достижения этой задачи?

+2

Вместо JOIN используется подзапрос для получения данных Agent_Contact. –

+0

Очень рекомендую внутреннее соединение вместо левого соединения. – HddnTHA

+1

@HddnTHA И почему? Вы понимаете, почему OP использует «LEFT JOIN»? Подсказка: «Там могут быть агенты, у которых также нет агента-агента». – sjagr

ответ

0

Поскольку нет правила, к которому должен быть возвращен контакт, достаточно добавить предложение group by.

SELECT Agent.*, 
Agent_Contact.* 
FROM Agent 
LEFT JOIN Agent_Contact ON Agent.idAgent = Agent_Contact.idAgent 
GROUP Agent.idAgent 
+1

Это не всегда работает. В некоторых системах вам потребуется использовать агрегатные функции в столбцах, отличных от idAgent. – LCIII

+0

@LCIII Я знаю, что это не сработает на MS SQL, но оно должно работать на mysql. О каких системах вы говорите? –

0

Если вы хотите только 1 agent_contact вернулся в agent вернулся тогда вопрос «который agent_contact вы хотите вернулся?»

Это как выбор классной комнаты, состоящей из 20 студентов и говорящего «Пожалуйста, верните 1 ученика». Ну ... какого студента ты хочешь?

Когда речь заходит о выборе Agent_Contact, вы можете выбрать то в алфавитном порядке, или один с самым длинным именем, или что-то , что позволит сократить число agent_contacts до 1.

Этот запрос выбирает agent_contact с максимальным именем. Вы можете использовать любой столбец agent_contact, который вам нужен, он просто должен быть помещен в агрегированную функцию, которая вернет только один вид.

SELECT t.Id, ac.* FROM 
(SELECT Agent.Id, Max(AgentContact.Name) 
FROM Agent 
LEFT JOIN Agent_Contact ON Agent.idAgent = Agent_Contact.idAgent 
GROUP BY Agent.Id) as t 
INNER JOIN Agent_Contact as ac ON t.Name = ac.Name 
Смежные вопросы