Предупреждение: нулевое значение удаляется агрегированием или другой операцией SET в Aqua Data Studio.

97

У меня проблема, когда данные равны нулю и при отображении результата появляется предупреждение. Как решить эту проблему?. Как изменить нулевые данные на 0, когда в таблице нет данных ?.

Это мой код: -

SELECT DISTINCT c.username             AS assigner_officer,
                d.description          AS ticketcategory,
                (SELECT Count(closed)
                 FROM   ticket
                 WHERE  assigned_to = c.user_id
                        AND closed IS NOT NULL
                 GROUP  BY assigned_to)closedcases,
                (SELECT Count(closed)
                 FROM   ticket
                 WHERE  assigned_to = c.user_id
                        AND closed IS NULL
                 GROUP  BY assigned_to)opencases
FROM   ticket a
       JOIN ticketlog b
         ON a.ticketid = b.ticketid
       JOIN access c
         ON a.assigned_to = c.user_id
       JOIN ticket_category d
         ON a.cat_code = d.id
       JOIN lookup_department e
         ON a.department_code = e.code 

Результат выглядит так: -

 Warnings: ---> 
   W (1): Warning: Null value is eliminated by an aggregate or other SET operation.
          <--- 
 assigner_officer     ticketcategory     closedcases     opencases    
 -------------------  -----------------  --------------  ------------ 
 abdulhafiz           Enquiry            (null)          0            
 affan                Enquiry            12              (null)       
 amirul               Enquiry            1               (null)       
 azrul_fahmi          Enquiry            45              0            
 Azwani               Enquiry            (null)          0            
 chai                 Enquiry            4               (null)       
 dalinawati           Enquiry            1               0            
 Emmy                 Complaints         (null)          0            
 Fadhlia              Enquiry            38              0            
 fairulhalif          Others             1               (null)       
 farikh               Enquiry            (null)          0            
 ismailh              Enquiry            28              0            
 izzahanna            Enquiry            (null)          0            
 Kamsuzilawati        Enquiry            1               (null)     
Амин ШОС
источник
1
Count(closed) ... WHERE ... closed IS NULLне имеет никакого смысла, поскольку COUNTтолько считает NOT NULLзначения
Мартин Смит
Я получаю такое же предупреждение. Я не возражаю против предупреждения само по себе, но мне нужно, чтобы хранимая процедура запускалась агентом SQL, и когда я это делаю, предупреждение приводит к сбою задания агента.
RichieACC
Этот вопрос не имеет смысла.
xr280xr

Ответы:

104

Вы в основном будете использовать COUNTдля суммирования по UID. Следовательно

COUNT([uid]) выдаст предупреждение:

Предупреждение: нулевое значение удаляется агрегированием или другой операцией SET.

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

Использование COUNT(*)в этом случае также приведет к неверным результатам, так как тогда вы будете подсчитывать общее количество результатов (т.е. родителей), которые существуют.

Использование COUNT([uid])IS - допустимый способ подсчета, а предупреждение - не более чем предупреждение. Однако, если вы обеспокоены и хотите получить истинное количество идентификаторов uid в этом случае, вы можете использовать:

SUM(CASE WHEN [uid] IS NULL THEN 0 ELSE 1 END) AS [new_count]

Это не добавит много накладных расходов к вашему запросу. (проверено mssql 2008)

Мэт Трахерн
источник
1
Я так искал и безуспешно пытался, но использование NULLIF в сочетании с ISNULL спасло меня. Вы можете попробовать комбинацию этих двух, например: ISNULL (NULLIF ([fieldValue], 0), 1)
QMaster
Разве решение специально для столбца «opencases» не было бы проще, чем просто «select count (1) ...» (или «count» любого другого литерала)? В предложении Where уже указано «and closed is NULL», поэтому нет необходимости суммировать оператор case в этом случае. Кроме того, я слышал (много лет назад), что «count (*)» не так эффективно, как подсчет одного столбца или литерала, но не уверен, так ли это до сих пор.
RowanPD
Вместо того count([uid]), чтобы использовать его count(1)?
Фархан
Вы, сэр @Mat Traherne, спасли меня :) Я получил это, пытаясь связать данные в файле Excel, уже было ISNULL (x, y), но это не сработало, однако "SUM (CASE, WHEN X IS NULL THEN 0 ELSE X КОНЕЦ) КАК Z "отлично поработал! Благодарность!
Димитрий
21

Один из способов решить эту проблему - отключить предупреждения.

SET ANSI_WARNINGS OFF;
GO
Мукус
источник
32
Из msdn это не только изменяет предупреждения о null в агрегатах, но также изменяет обработку ошибок деления на ноль и переполнения. Это приводит к тому, что это решение не подходит для меня.
Frédéric
3
Почему вы вообще считаете это проблемой? это просто информационное сообщение
Мартин Смит
2
@Mukus - Нет, это не так. Он распечатывает сообщение с уровнем серьезности 10. Значение 10 или ниже является информационным и не рассматривается как ошибка. SELECT SUM(X) FROM (VALUES ( 1 + NULL)) V(X);SELECT 'This is executed fine';
Мартин Смит
5
@RichieACC Да, потому что это не ответ, и отключение чрезвычайно желательных предупреждений ANSI как ленивого способа избежать одного информационного сообщения вызовет сбой во многих других, явно неинформационных вещах.
underscore_d
3
Решение проблемы включения контрольных ламп вашего автомобиля - просто отключить приборную панель. Это, вероятно, худший ответ, который я когда-либо видел в stackoverflow.
VoronoiPotato
18

Использование ISNULL(field, 0)Его также можно использовать с агрегатами:

ISNULL(count(field), 0)

Однако вы можете подумать об изменении count(field) to count(*)

Редактировать:

пытаться:

closedcases = ISNULL(
   (select count(closed) from ticket       
    where assigned_to = c.user_id and closed is not null       
    group by assigned_to), 0), 

opencases = ISNULL(
    (select count(closed) from ticket 
     where assigned_to = c.user_id and closed is null 
     group by assigned_to), 0),
Крис Гесслер
источник
У меня есть попытка, но (null) все еще существует в строке. Как изменить это значение на 0, когда данные равны нулю?
Amin SCO
спасибо, но ненулевое значение также имеет ту же проблему, когда появляется null. как изменить значение на 0 ?.
Amin SCO
1
FYI: ISNULL(count(field), 0)у меня не работал в MSSQL 2008 R2. Проблема заключалась в том, что я пытался подсчитать поле в левой внешней объединенной таблице, чтобы получить количество записей в объединенной таблице, связанных с основной таблицей. В итоге мне пришлось сделать подзапрос, который объединил две таблицы, чтобы получить количество идентификаторов в основной таблице. Подзапрос остался внешним, присоединенным к основной таблице по идентификатору. Затем счетчик подзапроса был заключен в ISNULL, чтобы получить желаемый 0 (без предупреждения).
Trisped
1
Крис, должно быть COUNT (ISNULL (Field, 0)), а не наоборот. При запросе текущего формата все, что будет возвращено, - это 0, а не реальное количество. Логика: Count (field) вернет один NULL для всех значений поля, которые равны NULL, а ISNULL установит его в 0, возвращая 0.
Говинд Рай,
10

Вы хотите поместить функцию ISNULLвнутри COUNT, а не снаружи:

Фигово: ISNULL(COUNT(field), 0)

ХОРОШИЙ: COUNT(ISNULL(field, 0))

Бен Гаррисон
источник
12
Это не правильно. count(ISNULL(field, 0))будет эквивалентно count(*), поскольку подсчитываемое значение больше не может быть NULL.
@hvd это не так, значение только 0, когда поле null.
Говинд Рай,
3
@GovindRai Нет, это действительно неправильно. Если вы считаете, что можете придумать контрпример, пример, COUNT(ISNULL(field, 0))который отличается от COUNT(*), пожалуйста, сделайте это, SQL Fiddle позволяет легко поделиться таким контрпримером. Но у тебя не получится. Поскольку COUNTподсчитывает ненулевые значения, даже если они равны нулю, и ISNULL(field, 0)всегда имеет ненулевое значение, COUNT(ISNULL(field, 0))подсчитывает строки. Это то COUNT(*), для чего, а не то, что здесь было после OP.
2
@hvd Вы правы. Мой ответ был основан на group byзапросе в другом контексте, чем то, что было после OP. В моем случае ISNULL(COUNT(field), 0)возвращал бы счетчик 0 для всех значений NULL, который был неверным, поскольку было несколько значений NULL, тогда как COUNT(ISNULL(field),0)вернул бы правильный счет для общего # значений NULL. Но опять же, два совершенно разных сценария.
Говинд Рай,
Получил, чтобы работать. Ну вот! sqlfiddle.com/#!3/ee0546/2 Проголосовал за ваш комментарий lol
Govind Rai
-2

Я получал эту ошибку; Я просто поместил WHEREпредложение для поля, которое использовалось в countпредложении. это решило проблему. Примечание: если существует нулевое значение, проверьте, является ли оно критичным для отчета, поскольку оно исключено из подсчета.

Старый запрос:

select city, Count(Emp_ID) as Emp_Count 
from Emp_DB
group by city

Новый запрос:

select city, Count(Emp_ID) as Emp_Count 
from Emp_DB
where Emp_ID is not null
group by city
хариишр
источник
-3

Если внутри агрегатной функции существует какое-либо значение Null, вы столкнетесь с этой проблемой. Вместо кода ниже

 SELECT Count(closed)
  FROM   ticket
  WHERE  assigned_to = c.user_id
  AND closed IS NULL

использовать как

SELECT Count(ISNULL(closed, 0))
  FROM   ticket
  WHERE  assigned_to = c.user_id
  AND closed IS NULL
Манив
источник