Отличный счетчик по массивам Bigquery - PullRequest
0 голосов
/ 24 сентября 2018

Я хочу объединить массивы между строками, а затем выполнить отдельный подсчет.В идеале это будет работать:

WITH test AS
(
  SELECT
  DATE('2018-01-01') as date,
  2 as value,
  [1,2,3] as key
  UNION ALL
  SELECT
  DATE('2018-01-02') as date,
  3 as value,
  [1,4,5] as key
)
SELECT
  SUM(value) as total_value,
  ARRAY_LENGTH(ARRAY_CONCAT_AGG(DISTINCT key)) as unique_key_count
FROM test

К сожалению, функция ARRAY_CONCAT_AGG не поддерживает оператор DISTINCT.Я могу удалить массив, но затем получаю разветвление, и сумма столбца значений неверна:

WITH test AS
(
  SELECT
  DATE('2018-01-01') as date,
  2 as value,
  [1,2,3] as key
  UNION ALL
  SELECT
  DATE('2018-01-02') as date,
  3 as value,
  [1,4,5] as key
)

SELECT
  SUM(value) as total_value,
  COUNT(DISTINCT k) as unique_key_count

FROM test
  CROSS JOIN UNNEST(key) k

enter image description here

Есть ли что-нибудь, что я 'м отсутствует, что позволило бы мне избежать присоединения в необязательный массив?

Ответы [ 2 ]

0 голосов
/ 24 сентября 2018

Ниже приведено для BigQuery Standard SQL

#standardSQL
WITH test AS
(
  SELECT DATE('2018-01-01') AS DATE, 2 AS value, [1,2,3] AS key UNION ALL
  SELECT DATE('2018-01-02') AS DATE, 3 AS value, [1,4,5] AS key
)
SELECT 
  total_value,
  COUNT(DISTINCT key) unique_key_count
FROM (
  SELECT
    SUM(value) AS total_value,
    ARRAY_CONCAT_AGG(key) AS all_keys
  FROM test
), UNNEST(all_keys) key
GROUP BY total_value  

результат:

Row total_value unique_key_count     
1   5           5     

Если в вашей таблице достаточно строк - вы можете легко добраться до памяти /проблема с ресурсами - в этом случае вы можете попробовать использовать функции HyperLogLog ++ для приблизительной агрегации - см. пример ниже

#standardSQL
WITH test AS
(
  SELECT DATE('2018-01-01') AS DATE, 2 AS value, [1,2,3] AS key UNION ALL
  SELECT DATE('2018-01-02') AS DATE, 3 AS value, [1,4,5] AS key
)
SELECT
  SUM(value) total_value,
  HLL_COUNT.MERGE((SELECT HLL_COUNT.INIT(key) FROM UNNEST(key) key)) AS unique_key_count
FROM test

с результатом

Row total_value unique_key_count     
1   5           5

Примечание: это приблизительноагрегации - обратите внимание на параметр precision в функции HLL_COUNT.INIT(input [, precision])

0 голосов
/ 24 сентября 2018

Вот альтернатива:

CREATE TEMP FUNCTION DistinctCount(arr ANY TYPE) AS (
  (SELECT COUNT(DISTINCT x) FROM UNNEST(arr) AS x)
);

WITH test AS
(
  SELECT
  DATE('2018-01-01') as date,
  2 as value,
  [1,2,3] as key
  UNION ALL
  SELECT
  DATE('2018-01-02') as date,
  3 as value,
  [1,4,5] as key
)

SELECT
  SUM(value) as total_value,
  DistinctCount(ARRAY_CONCAT_AGG(key)) as unique_key_count
FROM test

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

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