Oracle的管道函数(Pipelined)为实际工作中的商业应用提供高效的数据解决方案
实际应用场景
在实际工作中,在线销售系统对应的促销系统,因为促销逻辑的复杂性,而在实际开发和应用中,有时时刻刻都在使用商品的促销信息。因此,特别应用了Oracle的管道函数和对象类型技术。开创了并发多管道流式设计,为商品促销实时返回查询结果,从而为系统带来可观的性能提升。在电商系统,有126处引用,涉及30个文件。从而可知道其必要性。
- 对象类型的创建
对象类型,尤其适合于构建可重用的部件和复杂的应用程序的面向对象的编程。在PL / SQL,面向对象的程序设计是基于对象类型。他们坚持让你模拟现实世界的对象,单独的接口和实现细节,面向对象的数据和存储在数据库中。
下面是实际的促销信息数据对象,记录的一个商品经过计算后,对应促销信息。
CREATE OR REPLACE TYPE "OBJ_PRM_DETAIL_INFO" as object
(
sellerid number(7),
prmcode varchar2(60),
prmlevel varchar2(50),
prmdesc varchar2(80),
prmtype varchar2(120),
prmcomp varchar2(120),
prmcut varchar2(120),
prmmem varchar2(120),
prmtime varchar2(120),
prmzhenpin varchar2(120),
prmjifen varchar2(120),
prmticket varchar2(120),
prmpage varchar2(120),
skucode varchar2(60),
skuprice number(10,4),
skusumarr number(10,4),
skucutji number(10),
isshare varchar2(2),
prmtypeCode varchar2(3),--促销类型
prmcompCode varchar2(3),--计算方式
prmcutCode varchar2(3),--减价方式
cutvalue number(10,4), --减价额度
discountAmt number(10,4) --优惠金额
)
管道函数的创建
管道函数即是可以返回行集合(可以使嵌套表nested table 或数组 varray)的函数,我们可以像查询物理表一样查询它或者将其赋值给集合变量。
管道函数为并行执行,在普通的函数中使用dbms_output输出的信息,需要在服务器执行完整个函数后一次性的返回给客户端。如果需要在客户端
实时的输出函数执行过程中的一些信息,在oracle9i以后可以使用管道函数(pipeline function)。
关键字PIPELINED表明这是一个oracle管道函数,oracle管道函数的返回值类型必须为集合,在函数中,PIPE ROW语句被用来返回该集合的单个元
素,函数以一个空的RETURN 语句结束,以表明它已经完成。
由于管道函数的并发多管道流式设计以及实时返回查询结果而去除了中间环节因此可以带来可观的性能提升。
代码不完整,主要提现思想
create or replace function get_pip_prm_detail(i_SellerID in varchar2,
i_UserID in varchar2,
i_SkuID in varchar2,
i_ItemTypeCode in varchar2,
i_Qty in varchar2,
i_IsNotDetail in varchar2)
return pip_prm_detail
pipelined as
v_objtable obj_prm_detail_info;
/*
结果集:
PrmCode PrmLevel PrmDesc PrmType PrmComp PrmCut PrmMem PrmTime PrmZhenPin PrmTicket PrmPage
促销单号 促销等级 促销描述 促销类型 计算方式 减价方式 会员限制 限时值 是否赠品 是否赠券 单页类型
SkuCode SkuPrice SkuSumAmt BuyCount SalNum IsShare prmtypeCode prmcompCode prmcutCode cutvalue
SKU编码 促销价格 促销总价 购买数量 可售数量 是否可享 促销类型 计算方式 减价方式 额度
DiscountAmt
优惠金额
*/
begin
//此处省略相关业务处理逻辑
v_objtable := obj_prm_detail_info(i_SellerID, r_PrmCode,
r_PrmLevel, r_PrmDesc,
r_PrmType, r_PrmComp,
r_PrmCut, r_PrmMem,
r_PrmTime, r_PrmZhenPin,
r_PrmJiFen, r_PrmTicket,
r_PrmPage, r_SkuCode,
trunc(r_SkuPrice, 2),
trunc(r_SkuSumArr, 2),
r_SkuCutJi, r_IsShare,
v_PrmType, v_CompType,
v_CutType, r_CutValue,
r_DisCountAmt);
pipe row(v_objtable);
return;
end get_pip_prm_detail;
- Java中的调用方法
下面是在Mybatis中的应用,可以直接在SQL语句中使用:
select * from table(get_pip_prm_detail(#{sellerid},NVL(#{userid},NULL),#{skuid}, #{itemtypecode}, #{orderqty},'N')) a where a.isshare='Y'
4.结果集