#sql #sql-server
#sql #sql-сервер
Вопрос:
Мне всего два дня в SQL. Я пытаюсь обновить базу данных, в которой я хочу, чтобы в базе данных оставались только те строки для каждого уникального идентификатора, для которого серийный номер (Sl_No.) является наивысшим, а inspection_type содержит «PMCR».
Снимок данных:-
Требуется вывод:-
Ниже приведен код, который я мог бы написать до сих пор.
select * from (
Select Identifier,
Sl_No,
Inspection_Type,
RANK() Over (Partition by Identifier Order By SI_No Desc) AS Rnk
from copy_of_inspection_response
where (Inspection_Type like '%PMCR%')
)
Ошибка, которую я получаю, это :-
Я перепробовал все, но не могу найти какое-либо решение и не уверен, почему оно показывает синтаксическую ошибку,
Любая помощь будет высоко оценена!!
Спасибо!!
Комментарии:
1. Нет необходимости в подзапросе, просто сделайте
Select Identifier, ... from copy_of_inspection_response where Inspection_Type like '%PMCR%'
.
Ответ №1:
просто добавьте псевдоним в конце вложенного запроса.
select * from (
Select Identifier,
Sl_No,
Inspection_Type,
RANK() Over (Partition by Identifier Order By SI_No Desc) AS Rnk
from copy_of_inspection_response
where (Inspection_Type like '%PMCR%')
) u
Ответ №2:
Использование псевдонима после вашего последнего «)» исправит ошибку, но не даст ожидаемого результата. Вам нужно выбрать одну строку с наибольшим si_no для каждого идентификатора.
Пожалуйста, используйте следующий запрос
with cte as (
Select Identifier,
Sl_No,
Inspection_Type,
Rank() Over (Partition by Identifier Order By SI_No Desc) AS Rnk
from copy_of_inspection_response
where (Inspection_Type like '%PMCR%')
)
select * from cte where Rnk=1
Чтобы удалить все остальные строки, используйте запрос ниже:
with cte as (
Select Identifier,
Sl_No,
Inspection_Type,
Rank() Over (Partition by Identifier Order By SI_No Desc) AS Rnk
from copy_of_inspection_response
where (Inspection_Type like '%PMCR%')
) delete cte where Rnk>1
Комментарии:
1. Это работает, но не удаляет необязательные строки, не могли бы вы помочь мне, как это сделать в рамках одного запроса
2. Добавлен запрос для удаления нужных строк.
3. @ss_0708 Пожалуйста, дайте мне знать ваши отзывы.
4. Да, это помогло, большое спасибо
Ответ №3:
Используйте not exists
следующим образом:
select * from copy_of_inspection_response t
where t.Inspection_Type like '%PMCR%'
and not exists
(select 1 from copy_of_inspection_response tt
where tt.Identifier = t.Identifier
and tt.Inspection_Type like '%PMCR%'
and tt.SI_No > t.SI_No )
Если вы хотите delete
из таблицы, используйте exists
следующее:
delete from t
from copy_of_inspection_response t
where t.Inspection_Type like '%PMCR%'
and exists
(select 1 from copy_of_inspection_response tt
where tt.Identifier = t.Identifier
and tt.Inspection_Type like '%PMCR%'
and tt.SI_No > t.SI_No )
Комментарии:
1. Да ладно, у нас это было как агрегат окна, а вы переписали как самостоятельное объединение? Для чего? Все, что требовалось для операции, — это псевдоним
2. Я давал другой способ сделать то же самое. Что не так, если OP знает, как он может достичь одного и того же двумя разными способами.
3. Я знаю, но на самом деле вам также следует объяснить недостатки этого ответа (дополнительные запросы и т. Д.) @ ss_0708 Исправил это для вас
4. @Charlieface _ Большое вам спасибо, это сработало для меня,