Я пытаюсь проверить количество таблиц, но запрос непрерывно выполняется в течение 20 минут. Что может быть не так?

IF((select COUNT(1) from test.[dbo].[as_EmployeeData] (nolock) ed
JOIN test.[dbo].DepartmentData dd ON ed.EmployeeId= dd.DepartmentData
AND dd.Name = 'IT' AND dd.Status = 'Completed')= 0
)
BEGIN
PRINT 'Successful'
END
ELSE
BEGIN
PRINT 'Failed'
END

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

select COUNT(1) from test.[dbo].[as_EmployeeData] (nolock) ed
JOIN test.[dbo].DepartmentData dd ON ed.EmployeeId= dd.DepartmentData
AND dd.Name = 'IT' AND dd.Status= 'Completed'
-1
the_coder_guy 19 Янв 2022 в 15:37
1
Я подозреваю, что мы что-то упускаем здесь.
 – 
Larnu
19 Янв 2022 в 15:42
3
Вам не нужно (и не следует) считать, чтобы узнать, существуют ли какие-либо строки. Это может быть очень неэффективно. Используйте СУЩЕСТВУЮЩИЕ. И перестаньте засорять свой код nolock
 – 
SMor
19 Янв 2022 в 15:43
У вас есть подсказка «Меня не волнует точность» в одной таблице, но нет в другой. Блокировку проверяли? Есть ли у вас адекватные индексы, которые делают объединение эффективным? В любом случае – Плохие привычки — подсчет строк Трудный путь
 – 
Aaron Bertrand
19 Янв 2022 в 15:44
Я попробовал это, но все еще занимает столько же времени: IF NOT EXISTS(select 1 from test.[dbo].[as_EmployeeData] (nolock) ed JOIN test.[dbo].DepartmentData dd ON ed.EmployeeId= dd.DepartmentData AND dd.Name = 'IT' AND dd.Status = 'Completed' ) BEGIN PRINT 'Successful' END ELSE BEGIN PRINT 'Failed' END @SMor
 – 
the_coder_guy
19 Янв 2022 в 15:52
Возможно, если бы мы знали, ПОЧЕМУ вы пытаетесь это сделать, мы могли бы немного лучше указать вам правильное направление...
 – 
Andrew Corrigan
19 Янв 2022 в 16:35

3 ответа

Один из вариантов - вставить его в переменную:

DECLARE @myCount INT = (SELECT COUNT(1) 
                        FROM test.[dbo].[as_EmployeeData] ed
                             INNER JOIN test.[dbo].DepartmentData dd 
                                        ON dd.DepartmentData = ed.EmployeeId 
                                           AND dd.Name = 'IT' 
                                           AND dd.Status= 'Completed');

IF @myCount != 0
BEGIN 
    PRINT 'Successful'
END
ELSE
BEGIN
    PRINT 'Failed'
END

Однако COUNT будет постепенно становиться все более и более неэффективным по мере ввода все большего количества данных.

Лучше всего выполнить проверку EXISTS:

IF EXISTS (SELECT TOP 1 1 
           FROM test.[dbo].[as_EmployeeData] ed
                INNER JOIN test.[dbo].DepartmentData dd 
                           ON dd.DepartmentData = ed.EmployeeId 
                              AND dd.Name = 'IT' 
                              AND dd.Status= 'Completed')
BEGIN
     PRINT 'Successful'
END
ELSE 
BEGIN
     PRINT 'Failed'
END

Тем не менее, я не вижу логической причины для такого запроса; что еще вы делаете в блоке if/else?

0
Andrew Corrigan 19 Янв 2022 в 17:34

Вы можете попробовать сделать top 1 вместо подсчета, а затем использовать exists

IF ( exists( select top 1 1
             from test.[dbo].[as_EmployeeData] ed
               JOIN test.[dbo].DepartmentData dd 
                 ON ed.EmployeeId = dd.DepartmentData
                AND dd.Name = 'IT' 
                AND dd.Status = 'Completed'
           )
   )
BEGIN
  PRINT 'Successful'
END
ELSE
BEGIN
  PRINT 'Failed'
END
0
GuidoG 19 Янв 2022 в 17:37
IF NOT EXISTS(SELECT 1 
            FROM test.[dbo].[as_EmployeeData] AS ED WITH(NOLOCK)
                INNER JOIN test.[dbo].DepartmentData AS DD WITH(NOLOCK) ON ED.EmployeeId = DD.DepartmentData
            WHERE DD.[Name] = 'IT' AND DD.[Status] = 'Completed')
BEGIN
    PRINT 'Successful'
END
ELSE
BEGIN
    PRINT 'Failed'
END
-1
Toby 19 Янв 2022 в 16:59
Я пробовал то же самое, но запрос продолжает выполняться
 – 
the_coder_guy
19 Янв 2022 в 17:20