DB::Exception: Scalar subquery returned empty result

844 views
Skip to first unread message

rasmus

unread,
Jul 11, 2016, 10:26:54 AM7/11/16
to ClickHouse
Возникла такая проблема: при составлении запроса с подзапросом, в котором подзапрос возращает count() получаю ошибку типа "DB::Exception: Scalar subquery returned empty result".
Пример запроса:
SELECT x, (SELECT count() FROM test WHERE field=42 ) FROM test GROUP BY x UNION ALL SELECT x, (SELECT count() FROM test WHERE field2=32 ) FROM test GROUP BY x
Т.е. получается, что "SELECT count() FROM test WHERE field=42" возвращает Ok. вместо 0 и из-за этого получается ошибка.
Подскажите, пожалуйста, это баг или возможно я что-то неправильно делаю?

rasmus

unread,
Jul 11, 2016, 10:54:01 AM7/11/16
to ClickHouse
Уточню, может не совсем верно выразился. Проблема не в функции count(), а в том, что подзапрос ничего не возвращает(0 rows in set.) из-за ограничений(условий WHERE), поэтому и получаю такую ошибку

man...@gmail.com

unread,
Jul 11, 2016, 6:56:29 PM7/11/16
to ClickHouse
Эта такая (документированная) особенность поведения GROUP BY, не соответствующая стандарту SQL.

"Но, в отличие от стандартного SQL, если в таблице нет строк (вообще нет или после фильтрации с помощью WHERE), в качестве результата возвращается пустой результат, а не результат из одной строки, содержащий "начальные" значения агрегатных функций."

В будущем придётся изменить это поведение (возможно, добавив настройку).

Пока есть два способа это обойти:
1. Выполнять скалярные подзапросы по-отдельности.
2. Использовать запрос типа такого:

SELECT count() - 1 FROM (SELECT CounterID FROM test.hits WHERE CounterID = 123 UNION ALL SELECT toUInt32(1))

- мне это решение не нравится, так как оно неудобное и неестественное.

rasmus

unread,
Jul 12, 2016, 2:33:26 AM7/12/16
to ClickHouse
И вправду поведение и решение не естественное, поэтому хотелось бы, что настройка была добавлена. Спасибо!

Tima Ber

unread,
Sep 14, 2016, 2:54:18 AM9/14/16
to ClickHouse
Здраствуйте. Скажите пожалуйста, когда можно ожидать изменения?

man...@gmail.com

unread,
Sep 14, 2016, 2:15:52 PM9/14/16
to ClickHouse
Не было времени доделать.
Тем не менее, у нас есть спрос на эту задачу, а значит, мы скоро её сделаем.
Конкретные сроки сказать не могу.

Ярослав Коротаев

unread,
Jan 12, 2017, 4:59:28 AM1/12/17
to ClickHouse
Добрый день!
Какие-нибудь новости?

Кактус

unread,
Jan 12, 2017, 5:32:59 AM1/12/17
to ClickHouse


вторник, 12 июля 2016 г., 1:56:29 UTC+3 пользователь man...@gmail.com написал:
Эта такая (документированная) особенность поведения GROUP BY, не соответствующая стандарту SQL.


Пока есть два способа это обойти:
1. Выполнять скалярные подзапросы по-отдельности.
2. Использовать запрос типа такого:

SELECT count() - 1 FROM (SELECT CounterID FROM test.hits WHERE CounterID = 123 UNION ALL SELECT toUInt32(1))

- мне это решение не нравится, так как оно неудобное и неестественное.

А есть ли lifehack для обычного запроса SELECT count() FROM foo WHERE aaa < 0 ?
SELECT count() -1  FROM foo WHERE aaa < 0  не помогает


Ярослав Коротаев

unread,
Jan 12, 2017, 7:23:52 AM1/12/17
to ClickHouse
Временно можно решить проблему заворачивая подзапрос в такую конструкцию:

SELECT amount
FROM 
(
    SELECT sum(value) AS amount
    FROM payments 
    WHERE (date = toDate('2017-01-12'))
    UNION ALL 
    SELECT toFloat64(0)
LIMIT 1

Это вернет нужную сумму по колонке value, либо 0 если данных не было. Но это костыль, и нужно самому беспокоиться о соответствии типа данных в правой части объединения.

man...@gmail.com

unread,
Jan 13, 2017, 9:44:03 PM1/13/17
to ClickHouse
Первый подход к реализации этой задачи оказался неудачным - сложностей больше, чем ожидалось.
А второй подход запланирован после серьёзной подготовительной части, связанной с доработками совместимости с SQL - мы сейчас этим занимаемся.

четверг, 12 января 2017 г., 12:59:28 UTC+3 пользователь Ярослав Коротаев написал:
Добрый день!
Какие-нибудь новости?
Reply all
Reply to author
Forward
0 new messages