как устранить повторяющиеся результаты из присоединенного оператора SQL - PullRequest
0 голосов
/ 23 ноября 2011

У меня есть четыре таблицы, которые связаны следующим образом:

TABLE A: 1 to many with TABLE B
TABLE B: 1 to many with TABLE C
TABLE D: many to 1 with TABLE B

Я хотел бы создать набор результатов, который не содержит дубликатов.

SELECT A.f1
       A.f2
       B.f1
       C.f1
       D.f1
from   A LEFT JOIN (B INNER JOIN D on D.fk_b = B.id) on A.id = B.fk_a
         LEFT JOIN C on C.fk_b = B.id

Некоторые, но не все записи дублируются. Только записи от TABLE D с одинаковым FK до TABLE B.

Если есть 2 одинаковых поля D.fk_B, то я бы хотел выбрать только первое. Мой INNER JOIN станет чем-то вроде:

B INNER JOIN TOP 1 D on..... 

Но это не возможно?

Спасибо!

Ответы [ 3 ]

2 голосов
/ 09 апреля 2013

Предполагая, что рассматриваемая структура находится рядом с показанной ниже,

Tables

Следующий оператор SELECT покажет вам только первичные ключи, кратко давая представление о том, какие данные возвращаются.

SELECT
  A.id AS `A_id`,
  B.id AS `B_id`,
  COALESCE(C.id, 0) AS `C_id`,
  COALESCE(
    (SELECT D.id FROM D WHERE D.fk_b = B.id LIMIT 1), 0
  ) AS `D_id`
FROM B
INNER JOIN A ON (B.fk_a = A.id)
LEFT JOIN C ON (B.id = C.fk_b);

Теперь выбранный вами запрос:

SELECT
  A.f1 AS `A_f1`,
  A.f2 AS `A_f2`,
  B.f1 AS `B_f1`,
  COALESCE(C.f1, '-') AS `C_f1`,
  COALESCE(
    (SELECT D.f1 FROM D WHERE D.fk_b = B.id LIMIT 1), '-'
  ) AS `D_f1`
FROM B
INNER JOIN A ON (B.fk_a = A.id)
LEFT JOIN C ON (B.id = C.fk_b);

Код выше был протестирован и отлично работал на MySQL 5.6

0 голосов
/ 23 ноября 2011

Похоже, у вас есть декартово соединение.

Вы можете попытаться просто поместить DISTINCT перед определением столбца, или вы можете использовать подзапросы, чтобы связать таблицы вместе.

0 голосов
/ 23 ноября 2011

Попробуйте

SELECT DISTINCT A.f1
       A.f2
       B.f1
       C.f1
       D.f1
from   A LEFT JOIN (B INNER JOIN D on D.fk_b = B.id) on A.id = B.fk_a
         LEFT JOIN C on C.fk_b = B.id

Вы можете сделать это:

B INNER JOIN TOP 1 D on..... 

Как это

B INNER JOIN (SELECT TOP 1 fields from table) D ON ...

Попробуйте это:

  SELECT DISTINCT A.f1
           A.f2
           B.f1
           C.f1
           D.f1
    from   A 
    LEFT JOIN (B INNER JOIN (SELECT DISTINCT fk_b FROM D) D on D.fk_b = B.id) 
         on A.id = B.fk_a
    LEFT JOIN C on C.fk_b = B.id
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...