gpt4 book ai didi

oracle - Oracle PL/SQL 中的回调函数

转载 作者:行者123 更新时间:2023-12-04 13:50:29 25 4
gpt4 key购买 nike

我一直在用 PL/SQL 进行一些数据转换/处理,我想从我的包中消除重复代码。这是相关的代码部分。

表函数的输入类型:

type t_legs_cur is ref cursor return legs%rowtype;  

处理一条记录的过程:

procedure discontinuity_rule(p_leg in out nocopy legs%rowtype) as
begin
null; --business logic here
end discontinuity_rule;

迭代游标的表函数,处理游标中的每一行并通过管道输出(如果有):

function apply_discontinuity_rule(p_cur t_legs_cur)
return t_legs pipelined
order p_cur by (/* some fields */)
parallel_enable (partition p_cur by range (/* some fields */))
as
v_leg legs%rowtype;
begin
loop
fetch p_cur into v_leg;
exit when p_cur%notfound;

discontinuity_rule(v_leg); --call back

if v_leg.id is not null then
pipe row (v_leg);
end if;

end loop;
end apply_discontinuity_rule;

转换/处理有几个步骤,例如我将运行以下选择来执行一些处理并按给定顺序应用一些规则:

select * from table(trip_rules.generate_trips_from_legs(cursor(
select * from table(trip_rules.apply_5_legs_rule(cursor(
select * from table (trip_rules.apply_previous_city_rule(cursor(
select * from table (trip_rules.apply_backhaul_rule(cursor(
select * from table(trip_rules.apply_connection_time_rule(cursor(
select * from table(trip_rules.apply_discontinuity_rule(cursor(
select * from table(trip_rules.generate_legs_from_input(cursor(
select * from INPUT_DATA
)))
)))
)))
)))
)))
)))
)));

一切都很好,唯一的问题是,我的 trip_rule 包包含许多 apply_*_rule 函数。它们都类似于示例 apply_discontinuity_rule。唯一的区别是它们回调的实际过程 (discontinuity_rule)。

所以,我的问题是,如何避免复制 apply_* 函数的代码。有没有更优雅的方法来做到这一点,然后使用一个大的 if:if p_rule_name == 'discontinuity_rule' then

function apply_rule(p_cur t_legs_cur, p_rule_name in varchar2)
return t_legs pipelined
order p_cur by (/* some fields */)
parallel_enable (partition p_cur by range (/* some fields */))
as
v_leg legs%rowtype;
begin
loop
fetch p_cur into v_leg;
exit when p_cur%notfound;

if p_rule_name == 'discontinuity_rule' then
discontinuity_rule(v_leg);
elsif p_rule_name == 'other_rule' then
other_rule(v_leg);
elsif p_rule_name == 'totally_other_rule' then
totally_other_rule(v_leg);
-- and so on...
end if;

if v_leg.id is not null then
pipe row (v_leg);
end if;

end loop;
end apply_rule;

我还了解到,可以使用过程名称即时创建匿名 PL/SQL block 并将其作为动态 SQL 执行。我想知道它是否可以正确完成,而不会影响我的表现。任何想法表示赞赏。

最佳答案

您的巨型 IF 语句不是重复代码。

没错,它有彼此相似的部分,但是这个......

elsif p_rule_name == 'other_rule' then
other_rule(v_leg);

...绝对与此不同...

elsif p_rule_name == 'totally_other_rule' then
totally_other_rule(v_leg);

除非别无选择,否则我们应该避免使用动态 PL/SQL。这里不需要。

关于oracle - Oracle PL/SQL 中的回调函数,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/12974284/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com