T-SQL Delete дублирует, оставляя один с максимальным значением из другой таблицы - PullRequest
0 голосов
/ 17 апреля 2019

Я бы хотел попросить вас о помощи в создании запроса для удаления дубликатов, но при этом оставив запись с максимальным значением из другой таблицы.

У меня есть особый дизайн базы данных SQL Server.

Таблица Основная :

|ID|  URL     | some other columns
+--+----------+
|1 |  URL1    |
|2 |  URL1    | 
|3 |  URL2    |

Таблица Популярные :

|ID|  MainID  |UseCount | SearchString
+--+----------+---------+--------------
|1 |  3       | 124     | Phrase1
|2 |  2       | 234     | Phrase2
|3 |  1       | 123     | Phrase3
|4 |  1       | 7       | Phrase4

Итак, в таблице Main у меня есть список URL, где некоторые из них дублируются. В таблице Populars у меня есть записи с UseCount каждого URL - здесь может быть более одной записи для одного URL, where Main.ID = Populars.MainID, но может также не быть связанной записи в Populars для записи в Main.

Проблема в том, чтобы удалить дубликаты из Main, оставив тот, который имеет самый высокий UseCount в Populars.

Я пробовал несколько подходов, но не нашел решения ...

Этот запрос:

WITH ToDelete AS 
(
    SELECT 
        *,
        RN = ROW_NUMBER() OVER (PARTITION BY URL ORDER BY id) 
    FROM 
        Main
)
DELETE FROM ToDelete 
WHERE RN > 1

правильно удаляет дубликаты, но оставляет «случайную» (с точки зрения UseCount) запись.

У меня также есть идея создать дополнительный столбец в таблице Main, сопоставить все URL-адреса в Main с MAX(Usecount) из Populars и вставить это значение в новый столбец, а затем попытаться удалить дубликаты. Это решило бы проблему с несколькими записями в Populars, относящимися к каждому URL в main ...

Однако я не очень разбираюсь в SQL-запросах ...

В самом конце также должны быть удалены бесхозные записи (которые не имеют связанных записей в основном) из Populars.

Я не нашел ничего подходящего для моей проблемы - все подобные вопросы связаны с данными только в одной таблице - я борюсь с этим в течение нескольких дней, пытаясь найти решение.

У вас есть какие-нибудь идеи для достижения результата?

1 Ответ

0 голосов
/ 17 апреля 2019

ОК, я нашел решение.

Я создал представление:

create view [dbo].[MainWithUseCount] 
as
select  *, (select max(usecount) as MaxUseCont from [dbo].[Populars] where MainID = ID) as MaxUseCount from Main 
GO

И после этого использовали:

        WITH ToDelete AS 
        (SELECT *,RN=ROW_NUMBER() OVER(PARTITION BY URL ORDER BY MaxUseCount DESC) 
         FROM MainWithUseCount)
 delete FROM ToDelete WHERE RN>1

Что сработало хорошо.

Теперь вы можете проголосовать за мой вопрос столько, сколько хотите ...

...