如何在 BigQuery 中取消嵌套重复记录,一个数组给出列名,另一个给出列值?
Posted
技术标签:
【中文标题】如何在 BigQuery 中取消嵌套重复记录,一个数组给出列名,另一个给出列值?【英文标题】:How can I unnest a repeated record in BigQuery, with one array giving the column names and another giving column values? 【发布时间】:2021-04-30 12:44:21 【问题描述】:我在 Google BigQuery 中工作,并且有一个包含两条重复记录的数据集:一条是元素名称,另一条是元素值。我的数据集的简化版本(只有 2 个条目)如下所示:
globalId | Meta.name | Meta.value |
---|---|---|
9200000104 | ViewsL7D | 2877 |
OldPrice | 33.47 | |
NewPrice | 33.21 | |
9200000783 | ViewsL7D | 19231 |
OldPrice | 14.27 | |
NewPrice | 12.11 |
我想要的是这样的表格:
globalId | ViewsL7D | OldPrice | NewPrice |
---|---|---|---|
9200000104 | 2877 | 33.47 | 33.21 |
9200000783 | 19231 | 14.27 | 12.11 |
我之前没有处理过重复记录,所以我真的不知道如何解决这个问题,但到目前为止我已经尝试使用以下代码:
SELECT * FROM table LEFT JOIN UNNEST(cloudmetadata)
但是当我这样做时,我保留了重复的记录,只添加了六个额外的列,在名称和值之间交替。有人可以帮忙吗?
【问题讨论】:
【参考方案1】:您可以简单地旋转表格
如果你有超过这三个肉名你必须使用动态sql
CREATE TABLE table1 ( `globalId` varchar(10), `Meta.name` VARCHAR(8), `Meta.value` DECIMAL(10,2) );
✓
INSERT INTO table1 (`globalId`, `Meta.name`, `Meta.value`) VALUES ('9200000104', 'ViewsL7D', '2877'), ('9200000104', 'OldPrice', '33.47'), ('9200000104', 'NewPrice', '3321'), ('9200000783', 'ViewsL7D', '19231'), ('9200000783', 'OldPrice', '14.27'), ('9200000783', 'NewPrice', '12.11');
全球标识 |视图L7D |旧价格 |新价格 :--------- | --------: | --------: | --------: 9200000104 | 2877.00 | 33.47 | 3321.00 9200000783 | 19231.00 | 14.27 | 12.11SELECT `globalId`, MAX(IF (`Meta.name` = 'ViewsL7D',`Meta.value`, NULL )) AS ViewsL7D, MAX(IF (`Meta.name` = 'OldPrice',`Meta.value`, NULL )) AS OldPrice, MAX(IF (`Meta.name` = 'NewPrice',`Meta.value`, NULL )) AS NewPrice FROM table1 GROUP BY `globalId`
db小提琴here
【讨论】:
【参考方案2】:考虑以下方法
select globalId,
max(if(name = 'ViewsL7D', value, null)) as ViewsL7D,
max(if(name = 'OldPrice', value, null)) as OldPrice,
max(if(name = 'NewPrice', value, null)) as NewPrice
from your_table t, t.Meta
group by globalId
如果应用于您问题中的样本数据
输出是
【讨论】:
你有机会尝试吗?【参考方案3】:鉴于您的桌子的形状,我想您有两个数组 name
和 value
保存在 Meta
结构中。我使用以下内容重新创建了表:
WITH
mydata AS (
SELECT
9200000104 AS globalid,
STRUCT(["ViewsL7D",
"OldPrice",
"NewPrice"] AS name,
[2877,
33.47,
33.21] AS value) AS Meta
UNION ALL
SELECT
9200000783 AS globalid,
STRUCT(["ViewsL7D",
"OldPrice",
"NewPrice"] AS name,
[19231,
14.27,
12.11] AS value) AS Meta )
您想从那里取消嵌套数组并对其进行旋转:
SELECT
globalid,
MAX(IF(name="ViewsL7D",value, NULL)) AS ViewsL7D,
MAX(IF(name="OldPrice",value, NULL)) AS OldPrice,
MAX(IF(name="NewPrice",value, NULL)) AS NewPrice
FROM
(SELECT
globalid,
Meta.name[OFFSET(offset_value)] name,
Meta.value[OFFSET(offset_value)] value
FROM mydata,
UNNEST(Meta.value) value WITH OFFSET offset_value ORDER BY offset_value)
GROUP BY globalid
ORDER BY
globalid
它给出了这个
【讨论】:
以上是关于如何在 BigQuery 中取消嵌套重复记录,一个数组给出列名,另一个给出列值?的主要内容,如果未能解决你的问题,请参考以下文章