使用Oracle PLSQL从动态选择的表中合并唯一值的更有效方法
给定一个声明的PLSQL过程使用Oracle PLSQL从动态选择的表中合并唯一值的更有效方法,plsql,oracle10g,Plsql,Oracle10g,给定一个声明的PLSQL过程 PROCEDURE GET_DISTINCT_TIMES(dtypes IN VARCHAR2, start IN NUMBER, end IN NUMBER distinct_times_cursor OUT SYS_REFCURSOR) 其中: “Dtypes”是一个逗号分隔的字符串,每个值对应于我要检索的一般类型的数据。一种数据类型可能对应于需要检索不同时间的一个或多个不同表 “开始”和“结束”是我正在查询的两个时间 我已经编写了使用联合动态创建S
PROCEDURE GET_DISTINCT_TIMES(dtypes IN VARCHAR2, start IN NUMBER, end IN NUMBER
distinct_times_cursor OUT SYS_REFCURSOR)
其中:
- “Dtypes”是一个逗号分隔的字符串,每个值对应于我要检索的一般类型的数据。一种数据类型可能对应于需要检索不同时间的一个或多个不同表
- “开始”和“结束”是我正在查询的两个时间
- 当绑定变量的数量与传递给过程的参数完全可变时,将绑定变量与动态创建的SQL字符串相关联
- 采取不同的方法,对于每个数据类型-执行另一个存储过程或SQL语句,存储每个查询的记录集,然后合并唯一的结果并为新结果分配一个游标
另一种可能性是使用。对于每种数据类型,您将执行一个存储过程或SQL语句,并使用
PIPE ROW
输出结果。如果您仍然需要ref游标中的结果,可以执行SELECT*FROM TABLE(pipelined_function())
我四处询问,我的一个朋友想出了一个解决方案,我今天成功地实现了这个解决方案
基本上,我将整个PLSQL块动态创建为VARCHAR2,然后使用executeimmediate分配绑定变量。这个方法的好处是,我现在可以按名称而不是按位置分配绑定变量
以下是我的意思的一个例子:
var rs_cursor refcursor
DECLARE
start_tm CONSTANT PLS_INTEGER := 989452800;
end_tm CONSTANT PLS_INTEGER := 989452820;
plsql_block VARCHAR(1024);
BEGIN
plsql_block := 'BEGIN ' ||
'OPEN :rs_cursor FOR ' ||
' SELECT TIME ' ||
' FROM TBL_1 ' ||
' WHERE TIME BETWEEN :start_tm AND :end_tm ' ||
' UNION ' ||
' SELECT TIME ' ||
' FROM TBL_2 ' ||
' WHERE TIME BETWEEN :start_tm AND :end_tm ' ||
' ORDER BY TIME; ' ||
'END;';
EXECUTE IMMEDIATE plsql_block USING IN OUT :rs_cursor, IN start_tm, IN end_tm
END;
/
print rs_cursor
start_tm和end_tm只需传入一次,但应用于PLSQL块内的多个绑定
我的实际实现与此大不相同,但它使用了按名称执行即时绑定变量的特定功能,允许我根据提供给过程的任何数据类型动态创建SQL块。为什么不传入varchar2表而不是逗号分隔的列表?另外,更多的程序体将是有用的谢谢你的链接,我昨天开始尝试实现流水线表方法,但是从一个朋友那里找到了一个对我更有效的解决方案。虽然这些链接信息丰富,但我感谢您的输入!