Проблема SQL-соединения - объединение двух связанных запросов (полное внешнее соединение) - PullRequest
0 голосов
/ 29 марта 2012

Я боролся с этим уже несколько дней. Я не специалист по SQL, и мне удалось создать несколько запросов, однако у меня есть реальная работа по объединению запросов.

Например, я хочу объединить следующие два запроса:

SELECT publication_id AS Pure_Publication_Id, caa.person_id, 
    caa.name_first_name AS Primary_Author_First_Name, 
    caa.name_last_name AS Primary_Author_Last_Name
FROM pure.classified_author_assoc caa
    LEFT OUTER JOIN Pure.Publication
        ON Caa.Publication_Id = Publication.Id
WHERE Caa.Person_Id  IS NOT NULL
    AND publication.id IN
    (
        SELECT DISTINCT pure.publication_project_assoc.publication_id
        FROM Pure.project
            JOIN Pure.Publication_project_assoc
                ON project.id = Pure.Publication_project_assoc.project_id
        WHERE pure.project.source_id IN ('XEP378', 'XES049', 'YAH001')
    )
GROUP BY publication_id, caa.person_id, caa.name_first_name, caa.name_last_name;

и

SELECT publication.id AS Pure_Publication_Id
    COUNT (person_id) AS "NUMBER_OF_AUTHORS", 
    CASE WHEN COUNT (person_id) > 1 THEN 'Yes' 
        else 'No' END AS Additional_Authors
FROM pure.classified_author_assoc caa
    LEFT OUTER JOIN Pure.Publication
        ON Caa.Publication_Id = Publication.Id
WHERE Caa.Person_Id  IS NOT NULL
    AND publication.id IN
    (
        SELECT DISTINCT pure.publication_project_assoc.publication_id
        FROM Pure.project
            JOIN Pure.Publication_project_assoc
                ON project.id = Pure.Publication_project_assoc.project_id
        WHERE pure.project.source_id IN ('XEP378', 'XES049', 'YAH001')
    )
GROUP BY publication.id;

Я не могу объединить их в одном запросе (я не думаю), так как первый запрос вернул бы Number_of_authors как единое целое. Однако, когда я пытаюсь выполнить запрос, в середине будет полное объединение, как показано ниже, я получаю ошибку SQL, которая не завершилась должным образом, в конце первого оператора SQL, и я не уверен, что соединение должно быть в конец.

SELECT publication_id AS Pure_Publication_Id, caa.person_id, 
    caa.name_first_name AS Primary_Author_First_Name,
    caa.name_last_name AS Primary_Author_Last_Name
FROM pure.classified_author_assoc caa
    LEFT OUTER JOIN Pure.Publication
        ON Caa.Publication_Id = Publication.Id
WHERE Caa.Person_Id  IS NOT NULL
    AND publication.id IN
    (
        SELECT DISTINCT pure.publication_project_assoc.publication_id
        FROM Pure.project
            JOIN Pure.Publication_project_assoc
                ON project.id = Pure.Publication_project_assoc.project_id
        WHERE pure.project.source_id IN ('XEP378', 'XES049', 'YAH001')
    )
GROUP BY publication_id, caa.person_id, caa.name_first_name, caa.name_last_name
FULL OUTER JOIN
(
    SELECT publication.id AS Pure_Publication_Id, 
        COUNT (person_id) AS "NUMBER_OF_AUTHORS", 
        CASE WHEN COUNT (person_id) > 1 THEN 'Yes' 
            else 'No' END AS Additional_Authors
    FROM pure.classified_author_assoc caa
        LEFT OUTER JOIN Pure.Publication
            ON Caa.Publication_Id = Publication.Id
    WHERE Caa.Person_Id  IS NOT NULL
        AND publication.id IN
        (
            SELECT DISTINCT pure.publication_project_assoc.publication_id
            FROM Pure.project
                JOIN Pure.Publication_project_assoc
                    ON project.id = Pure.Publication_project_assoc.project_id
            WHERE pure.project.source_id IN ('XEP378', 'XES049', 'YAH001')
        )
)
GROUP BY publication.id
ON ****;

Я пробовал это всеми возможными способами и знаю, что это должно быть что-то простое. Кто-нибудь может помочь, пожалуйста?

Ответы [ 2 ]

1 голос
/ 29 марта 2012

Вы должны присоединиться ко второму запросу к предложению FROM первого. Мне также кажется, что вы, возможно, действительно после LEFT JOIN, а не FULL JOIN. Возможно, может помочь предложение WITH:

WITH q AS (
(SELECT publication.id AS Pure_Publication_Id, COUNT (person_id) AS "NUMBER_OF_AUTHORS", CASE WHEN COUNT (person_id) > 1 THEN 'Yes' else 'No' END AS Additional_Authors
...
)
SELECT publication_id AS Pure_Publication_Id, caa.person_id, caa.name_first_name AS Primary_Author_First_Name, caa.name_last_name AS Primary_Author_Last_Name, q.NUMBER_OF_AUTHORS, q.additional_authors 
  FROM pure.classified_author_assoc caa 
          LEFT OUTER JOIN Pure.Publication ON Caa.Publication_Id = Publication.Id
          LEFT OUTER JOIN q ON publication_id = q.pure_publication_id
 WHERE Caa.Person_Id  IS NOT NULL 
   AND publication.id IN 
       (SELECT DISTINCT pure.publication_project_assoc.publication_id
... 
0 голосов
/ 29 марта 2012

Это то, что вы ищете:

SELECT FirstQuery.*, SecondQuery.*
FROM
    (
        SELECT publication_id AS Pure_Publication_Id, caa.person_id, 
            caa.name_first_name AS Primary_Author_First_Name,
            caa.name_last_name AS Primary_Author_Last_Name
        FROM pure.classified_author_assoc caa
            LEFT OUTER JOIN Pure.Publication
                ON Caa.Publication_Id = Publication.Id
        WHERE Caa.Person_Id  IS NOT NULL
            AND EXISTS
            (
                SELECT 1 
                FROM Pure.project
                JOIN Pure.Publication_project_assoc
                    ON project.id = Pure.Publication_project_assoc.project_id
                WHERE pure.publication_project_assoc.publication_id = publication.id
                    AND pure.project.source_id IN ('XEP378', 'XES049', 'YAH001')
        )
        GROUP BY publication_id, caa.person_id, caa.name_first_name, caa.name_last_name
    ) AS FirstQuery
    FULL OUTER JOIN
    (
        SELECT publication.id AS Pure_Publication_Id, 
            COUNT (person_id) AS "NUMBER_OF_AUTHORS", 
            CASE WHEN COUNT (person_id) > 1 THEN 'Yes' 
                else 'No' END AS Additional_Authors
        FROM pure.classified_author_assoc caa
            LEFT OUTER JOIN Pure.Publication
                ON Caa.Publication_Id = Publication.Id
        WHERE Caa.Person_Id  IS NOT NULL
            AND EXISTS
            (
                SELECT 1 
                FROM Pure.project
                    JOIN Pure.Publication_project_assoc
                        ON project.id = Pure.Publication_project_assoc.project_id
                WHERE pure.publication_project_assoc.publication_id = publication.id
                    AND pure.project.source_id IN ('XEP378', 'XES049', 'YAH001')
            )
       GROUP BY publication.id
    ) AS SecondQuery
        ON FirstQuery.Pure_Publication_Id = SecondQuery.Pure_Publication_Id

Возможно, есть способ сделать это намного аккуратнее, но именно так вы должны выполнить свой FULL OUTER JOIN.Он использует вложенные запросы.Имейте в виду, что FULL OUTER JOIN вернет результаты NULL, если FirstQuery не имеет никакого значения.Итак, я предлагаю изменить его на LEFT JOIN.Это позволит убедиться, что в FirstQuery есть значение, но его не волнует, если в SecondQuery

ОБНОВЛЕНО ОБНОВЛЕНИЕ ДЛЯ ТОЧЕК И ОПТИМИЗАЦИИ

  • Добавляя publication.id IN, вы отменяете свой LEFT JOIN.Если вы хотите, чтобы он действительно был LEFT JOIN, тогда этот критерий фильтра должен быть включен в оператор LEFT JOIN s ON
  • Изменил ваш IN на EXISTS для сокращенияна беспорядок и достичь того же результата
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...