Сопоставить значение строки в столбце с именем другого столбца в BIGQUERY - PullRequest
0 голосов
/ 23 марта 2019

В bigquery, есть ли способ сделать операцию 'L'? Скажите где:

  +----------------+---------------+----------------+
  |     COL1       |      COL2     | FOO            |
  +----------------+---------------+----------------+
  | identif11      |   BAR         |     VALUE1     | 
  | identif22      |    FOO        |     VALUE2     | 
  +----------------+---------------+----------------+

, если значение в (COL2) соответствует (FOO) возвращаемому значению в (FOO), и, возможно, добавить его в новый столбец.

Я новичок в SQL, я мог бы сделать это в Python, но я имею дело с наборами данных миллионов строк, и мне нужно что-то более мощное здесь

L-оператор (COL1, FOO) должен вернуть VALUE2 во второй строке.

1 Ответ

3 голосов
/ 23 марта 2019

Ниже для BigQuery Standard SQL

Вариант 1

#standardSQL
SELECT col1, col2, foo, bar, 
  CASE col2 
    WHEN 'BAR' THEN bar
    WHEN 'FOO' THEN foo
  END L
FROM `project.dataset.table` t

Вы можете проверить, поиграть с выше, используя пример данных из вашего вопроса

#standardSQL
WITH `project.dataset.table` AS (
  SELECT 'identif11' col1, 'BAR' col2, 'VALUE1' foo, 'VALUE3' bar UNION ALL
  SELECT 'identif22', 'FOO', 'VALUE2', 'VALUE4'
)
SELECT col1, col2, foo, bar, 
  CASE col2 
    WHEN 'BAR' THEN bar
    WHEN 'FOO' THEN foo
  END L
FROM `project.dataset.table` t   

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

Row col1        col2    foo     bar     L    
1   identif11   BAR     VALUE1  VALUE3  VALUE3   
2   identif22   FOO     VALUE2  VALUE4  VALUE2   

Вариант 2

Вы можете немного «рефакторинг» выше - используя SQL UDF, как в примере ниже

#standardSQL
CREATE TEMP FUNCTION L(val STRING, t ANY TYPE) AS (
  CASE val 
    WHEN 'BAR' THEN t.bar
    WHEN 'FOO' THEN t.foo
  END  
);
WITH `project.dataset.table` AS (
  SELECT 'identif11' col1, 'BAR' col2, 'VALUE1' foo, 'VALUE3' bar UNION ALL
  SELECT 'identif22', 'FOO', 'VALUE2', 'VALUE4' UNION ALL
  SELECT 'identif22', 'AAA', 'VALUE2', 'VALUE4'
)
SELECT col1, col2, foo, bar, L(col2, t) L
FROM `project.dataset.table` t   

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

Row col1        col2    foo     bar     L    
1   identif11   BAR     VALUE1  VALUE3  VALUE3   
2   identif22   FOO     VALUE2  VALUE4  VALUE2   
3   identif22   AAA     VALUE2  VALUE4  null     

Вариант 3

И, наконец, версия, которая не требует заранее знать и ссылаться в коде явно на имена столбцов

#standardSQL
CREATE TEMP FUNCTION L(val STRING, t ANY TYPE) AS (
  REGEXP_EXTRACT(
    TO_JSON_STRING(t),
    CONCAT(r'(?i)"', val, '":"?([^"}]+)"?')
  ) 
);
SELECT col1, col2, foo, bar, L(col2, t) L
FROM `project.dataset.table` t   

Примечание: 3-й вариант не полностью протестирован и может иметь некоторые крайние случаи - но для простых случаев, таких как в ваших примерах данных - должен работать хорошо

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