sql - 更新 BQ 表中 5K 行的高效语法
问题描述
我正在尝试使用 python 客户端更新 bq 中的 ~5K 行。
这是我目前的尝试:
update_bq(table_id=_ADS_TO_REMOVE_TABLE_NAME, set_clasue="status ='removed'",
where_in_clause=f'''[{[item['ad_id'] for item in
current_ads_removed_json_chunk]}]''')
和
def update_bq(self, table_id, ad_ids, set_clasue, where_in_clause):
table_full_name = self.get_table_full_name(table_id)
query_text = f"""
UPDATE `{table_full_name}`
SET {set_clasue}
WHERE account_id IN {where_in_clause}
"""
query_job = self.client.query(query_text)
如何将 映射account id list
到如下看起来更有效的字符串(?)
UPDATE mytable SET somefield=( CASE WHEN (id=100) THEN 'some value removed' WHEN (id=101) THEN 'some value removed' END ) WHERE id IN (100,101);
我试过了:
f'''UPDATE mytable SET somefield=( CASE WHEN id={['(id=100) THEN some value \'removed\''.join( item['ad_id'] for item in current_ads_removed_json_chunk]}]+"WHERE id IN ("+ item['ad_id'] for item in current_ads_removed_json_chunk]);
另外 bq 自动时间戳是否会在更新时起作用(在插入时适用于我)。
仅删除具有这些 ID 的所有行并以新状态重新插入是否更好?
解决方案
我不知道这是否会更有效,但您可以尝试在 python 中创建整个 sql 脚本。脚本可以包含所有值。值将作为inject_table 传递,然后您可以使用signle 查询更新所有行。
文档:注入表和UPDATE FROM
with inject_table (
select 1 as col1, 2 as col2 UNION ALL
select 5 as col1, 3 as col2
)
update tt
set tt.val = it.col1
from target_table as tt
join inject_table as it on tt.col2 = it.col2
推荐阅读
- javascript - 非被动滚动事件处理程序的控制台警告
- redis - 如何在 Redis 中删除流的消费者?
- corda - 将一个cordapp作为corda jar依赖添加到其他corda项目
- kubernetes - 启用 webhook 身份验证 kubelet api
- java - JavaFX 帮助实现拖放
- java - 检索无法反序列化的 Kafka 消息的有效负载和标头
- c - 如何从 Windows 命名管道中读取超时?
- android - RestrictTo 不限制使用受限方法
- java - AES 加密函数返回 null
- linux - 无法生成预期结果的 Linux bash 脚本