避免在 Snowflake 中使用 LISTAGG 发出“字符串太长”警告

Avoid "String is too long" Warning with LISTAGG in Snowflake

提问人:Guido 提问时间:11/17/2023 最后编辑:Guido 更新时间:11/17/2023 访问量:42

问:

我一直在使用 Snowflake 中的 LISTAGG 函数来连接字符串,并触发了以下警告:

100078 (22000): String '(LISTAGG result)' is too long and would be truncated

我了解,当聚合字符串超过特定长度时,会触发此警告。我想知道防止或处理此警告的最佳实践,因为截断是好的,并且与列的质量无关。我应该提前截断结果吗?如果是这样,如何?

SELECT
        userid,
        NULLIF(LISTAGG(DISTINCT city, ', '), '') AS cities,
        NULLIF(LISTAGG(DISTINCT region, ', '), '') AS regions,
        ...
FROM {{ ref('myschema.table_T') }}
GROUP BY userid
sql snowflake-cloud-data-platform 截断 listagg

评论

0赞 Jonas Metzler 11/17/2023
我不明白你到底想知道什么。我们怎么知道什么是最适合您的查询?您将需要展示一些示例数据、预期结果并解释您不清楚的内容。
0赞 SelVazi 11/17/2023
你能分享完整的查询吗?
0赞 Guido 11/17/2023
嗨,两位,感谢您的反馈。我添加了它。

答:

0赞 SelVazi 11/17/2023 #1

由于聚合字符串达到限制,因此无法使用该函数。您可以创建一个用户定义的聚合函数:LISTAGG

create or replace function full_array_agg(g string, s string)
returns table (G string, S array)
language javascript
as $$
{
    processRow: function f(row, rowWriter, context){
        if( this.arr.indexOf(row.S) === -1 ) {
          this.arr.push(row.S)
        }
        this.group = row.G
        this.counter++;
    }
    , initialize: function(argumentInfo, context) {
        this.counter = 0;
        this.arr = [];
    }, finalize: function(rowWriter, context){
        rowWriter.writeRow({G:this.group, S: this.arr})
    }
}
$$;

你可以像这样使用它:

select cities.g as userid, cities.s as cities
from mytable
    , table(full_array_agg(
        userid::string, 
        city) over(partition by userid)) cities;

从这个答案中受到启发: