Snowflake Javascript UDF:嵌套在作为科学计数法发出的对象中的十进制值

Posted

技术标签:

【中文标题】Snowflake Javascript UDF:嵌套在作为科学计数法发出的对象中的十进制值【英文标题】:Snowflake Javascript UDFs: Decimal values nested within objects emitted as scientific notation 【发布时间】:2021-09-29 23:55:59 【问题描述】:

看起来 Snowflake UDF 默认使用科学记数法在对象类型(JSON 结构)中发出十进制值,即使这些值没有太多精度或很多有效数字。有没有办法阻止这种转换,或者有没有办法修改 UDF 以发出“更简单”的十进制值?

我希望保留对象结构,因此返回一个简单的标量十进制值不适合此用例(换句话说,返回一些简单的值并调用 TO_DECIMAL() 或类似的格式选项不合适解决方案——除非有创造性的用途)。

另外,对于这个用例,有必要传入整个对象,因为我正在对其执行一些递归处理,所以简单地通过 JSON 路径选择标量十进制值也不适合。

UDF 定义:

CREATE OR REPLACE FUNCTION F_DECIMAL(INPUT VARIANT)
RETURNS VARIANT
LANGUAGE javascript
AS
'
    return INPUT;
'

查询:

SELECT
    PARSE_JSON('"a": 1234.56789012345678901234, "b": 2.0, "c": 3, "d": 1739210.5, "e": 1234.567') AS json_parsed_simple,
    F_DECIMAL(PARSE_JSON('"a": 1234.56789012345678901234, "b": 2.0, "c": 3, "d": 1739210.5, "e": 1234.567')) AS json_udf

结果:

JSON_PARSED_SIMPLE JSON_UDF
"a": 1234.56789012345678901234, "b": 2, "c": 3, "d": 1739210.5, "e": 1234.567 "a": 1.234567890123457e+03, "b": 2, "c": 3, "d": 1.739210500000000e+06, "e": 1.234567000000000e+03

【问题讨论】:

【参考方案1】:

不能保证这将始终有效,但在这种情况下,返回一个字符串化对象并在 SQL 中使用 ::object 转换回一个对象会摆脱科学记数法:

CREATE OR REPLACE FUNCTION F_DECIMAL(INPUT VARIANT)
RETURNS variant
LANGUAGE javascript
AS
'
    return JSON.stringify(INPUT);
';

SELECT
    PARSE_JSON('"a": 1234.56789012345678901234, "b": 2.0, "c": 3, "d": 1739210.5, "e": 1234.567') AS json_parsed_simple,
    F_DECIMAL(PARSE_JSON('"a": 1234.56789012345678901234, "b": 2.0, "c": 3, "d": 1739210.5, "e": 1234.567'))::object AS json_udf

返回:


  "a": 1234.567890123457,
  "b": 2,
  "c": 3,
  "d": 1739210.5,
  "e": 1234.567

【讨论】:

谢谢;这很好用!因为我只描述了一般用例的特定部分,所以我可能会有后续行动,但这肯定有助于克服这个障碍。

以上是关于Snowflake Javascript UDF:嵌套在作为科学计数法发出的对象中的十进制值的主要内容,如果未能解决你的问题,请参考以下文章

雪花中的 JavaScript UDF

是否可以在 UDF 中调用 javascript 过程 API?

Snowflake 支持 Java UDF 的 JDK 版本是啥?

Snowflake DB UDF 可以执行 SQL 命令吗?

雪花 UDF 调用“显示共享”功能

Snowflake 存储过程中的最大 JavaScript 字符串大小