关于在 Snowflake 中的一个函数内嵌套多个函数的问题
Question regarding nesting multiple functions inside of a function in Snowflake
(代表 Snowflake 用户提交...)
问题:
是否可以在一个函数中嵌套多个函数并传递所有需要的参数?
例如...
CREATE OR REPLACE FUNCTION "udf_InteractionIndicator"("ROH_RENEWAL_SYSTEM_STATUS1" VARCHAR(100), "GOLS_OPPORTUNITY_LINE_STATUS" VARCHAR(100)
, "ROH_CLIENT_CURRENT_TEMPERATURE1" VARCHAR(100)
, "ROH_PO_ATTACHED" VARCHAR(100)
, "ROH_PO_NUMBER" VARCHAR(100)
, "RT_PAID_OVERRIDE" VARCHAR(100), "ROH_RENEWAL_OPPORTUNITY_STATUS1" VARCHAR(100)
, "ROH_RENEWAL_CONVERSATION_DATE" DATE, "ROH_APPROVAL_RECEIVED_DATE" DATETIME)
RETURNS NUMBER(1,0)
AS
$$
CASE WHEN ("udf_RenewalNoticeSentIndicator"("ROH_RENEWAL_SYSTEM_STATUS1", "ROH_CLIENT_CURRENT_TEMPERATURE1"
, "GOLS_OPPORTUNITY_LINE_STATUS"
, "ROH_PO_ATTACHED", "RT_PAID_OVERRIDE"
, "ROH_RENEWAL_OPPORTUNITY_STATUS1")) = 1
AND (ROH_RENEWAL_CONVERSATION_DATE IS NOT NULL
OR ("udf_AuthorizedIndicator"(ROH_APPROVAL_RECEIVED_DATE, "ROH_PO_ATTACHED", "ROH_PO_NUMBER")) = 1
OR ("udf_PaidIndicator"("GOLS_OPPORTUNITY_LINE_STATUS")) = 1
OR ("udf_ChurnIndicator"("GOLS_OPPORTUNITY_LINE_STATUS")) = 1
)
THEN 1 ELSE 0 END
$$
;
我收到了以下推荐:
...create a SQL UDF or JavaScript UDF. A JavaScript UDF can only
contain JavaScript code, and an SQL UDF can contain only one SQL
statement (no DML and DDL). In case of nesting, SQL UDF can call
another SQL UDF or a JavaScript UDF but the same is not true with the
JavaScript UDF(it only contains JavaScript code).
CREATE OR REPLACE FUNCTION udf_InteractionIndicator_nested(ID DOUBLE)
RETURNS DOUBLE
AS
$$
SELECT ID
$$;
create or replace function js_factorial(d double)
returns double
language javascript
strict
as '
if (D <= 0) {
return 1;
} else {
var result = 1;
for (var i = 2; i <= D; i++) {
result = result * i;
}
return result;
}
';
CREATE OR REPLACE FUNCTION udf_InteractionIndicator(ID DOUBLE)
RETURNS double
AS
$$
select udf_InteractionIndicator_nested(ID) + js_factorial(ID)
$$;
select udf_InteractionIndicator(4);
+-----------------------------+
| UDF_INTERACTIONINDICATOR(4) |
|-----------------------------|
| 28 |
+-----------------------------+
但是,我正在尝试使用 SQL UDF 来完成此操作。只要使用相同的参数,就可以创建嵌套函数,这是有道理的。我想创建一个接受 8 个参数的函数,并且底层函数可以引用父函数参数的全部、部分或 none。这就是我 运行 遇到问题的地方...想法?
(我们社区的一位顾问给出了以下答案...)
使用 JavaScript UDF,如果您的用例是 "main" 函数将工作分解为子函数,那么设计将更加紧凑和可维护主.
然后您只需在 main 函数中定义所有底层函数,这在 JavaScript 中是可能的,但在 SQL UDF 中是不可能的,然后您就可以在任何地方自由使用 main 参数。
CREATE OR REPLACE FUNCTION MAIN_JS(P1 STRING, P2 FLOAT)
RETURNS FLOAT
LANGUAGE JAVASCRIPT
AS '
function helper_1(p) { return p * 2; }
function helper_2(p) { return p == "triple" ? P2 * 3 : P2; }
return helper_1(P2) + helper_2(P1);
';
SELECT MAIN_JS('triple', 4); -- => 20
(代表 Snowflake 用户提交...)
问题:
是否可以在一个函数中嵌套多个函数并传递所有需要的参数?
例如...
CREATE OR REPLACE FUNCTION "udf_InteractionIndicator"("ROH_RENEWAL_SYSTEM_STATUS1" VARCHAR(100), "GOLS_OPPORTUNITY_LINE_STATUS" VARCHAR(100)
, "ROH_CLIENT_CURRENT_TEMPERATURE1" VARCHAR(100)
, "ROH_PO_ATTACHED" VARCHAR(100)
, "ROH_PO_NUMBER" VARCHAR(100)
, "RT_PAID_OVERRIDE" VARCHAR(100), "ROH_RENEWAL_OPPORTUNITY_STATUS1" VARCHAR(100)
, "ROH_RENEWAL_CONVERSATION_DATE" DATE, "ROH_APPROVAL_RECEIVED_DATE" DATETIME)
RETURNS NUMBER(1,0)
AS
$$
CASE WHEN ("udf_RenewalNoticeSentIndicator"("ROH_RENEWAL_SYSTEM_STATUS1", "ROH_CLIENT_CURRENT_TEMPERATURE1"
, "GOLS_OPPORTUNITY_LINE_STATUS"
, "ROH_PO_ATTACHED", "RT_PAID_OVERRIDE"
, "ROH_RENEWAL_OPPORTUNITY_STATUS1")) = 1
AND (ROH_RENEWAL_CONVERSATION_DATE IS NOT NULL
OR ("udf_AuthorizedIndicator"(ROH_APPROVAL_RECEIVED_DATE, "ROH_PO_ATTACHED", "ROH_PO_NUMBER")) = 1
OR ("udf_PaidIndicator"("GOLS_OPPORTUNITY_LINE_STATUS")) = 1
OR ("udf_ChurnIndicator"("GOLS_OPPORTUNITY_LINE_STATUS")) = 1
)
THEN 1 ELSE 0 END
$$
;
我收到了以下推荐:
...create a SQL UDF or JavaScript UDF. A JavaScript UDF can only contain JavaScript code, and an SQL UDF can contain only one SQL statement (no DML and DDL). In case of nesting, SQL UDF can call another SQL UDF or a JavaScript UDF but the same is not true with the JavaScript UDF(it only contains JavaScript code).
CREATE OR REPLACE FUNCTION udf_InteractionIndicator_nested(ID DOUBLE) RETURNS DOUBLE AS $$ SELECT ID $$; create or replace function js_factorial(d double) returns double language javascript strict as ' if (D <= 0) { return 1; } else { var result = 1; for (var i = 2; i <= D; i++) { result = result * i; } return result; } '; CREATE OR REPLACE FUNCTION udf_InteractionIndicator(ID DOUBLE) RETURNS double AS $$ select udf_InteractionIndicator_nested(ID) + js_factorial(ID) $$; select udf_InteractionIndicator(4); +-----------------------------+ | UDF_INTERACTIONINDICATOR(4) | |-----------------------------| | 28 | +-----------------------------+
但是,我正在尝试使用 SQL UDF 来完成此操作。只要使用相同的参数,就可以创建嵌套函数,这是有道理的。我想创建一个接受 8 个参数的函数,并且底层函数可以引用父函数参数的全部、部分或 none。这就是我 运行 遇到问题的地方...想法?
(我们社区的一位顾问给出了以下答案...)
使用 JavaScript UDF,如果您的用例是 "main" 函数将工作分解为子函数,那么设计将更加紧凑和可维护主.
然后您只需在 main 函数中定义所有底层函数,这在 JavaScript 中是可能的,但在 SQL UDF 中是不可能的,然后您就可以在任何地方自由使用 main 参数。
CREATE OR REPLACE FUNCTION MAIN_JS(P1 STRING, P2 FLOAT)
RETURNS FLOAT
LANGUAGE JAVASCRIPT
AS '
function helper_1(p) { return p * 2; }
function helper_2(p) { return p == "triple" ? P2 * 3 : P2; }
return helper_1(P2) + helper_2(P1);
';
SELECT MAIN_JS('triple', 4); -- => 20