oracle numlist,oracle sql str2numlist numtabletype
在实际使用中,经常会有带in的子查询,如where id in (1,2,3)这样的情况,但是如果很多这样的语句在数据库中出现,将引起数据库的大量硬解析与共享池SQL碎片。所以,在实际应用中,可以采用其他方法,将这些in list给绑定起来。
如果需要绑定in list,首先,需要创建两个类型(type):
针对数据类型的
CREATEOR REPLACE TYPE NUMTABLETYPE as table of number;
针对字符串类型的(每个list的单元大小不要超过1000字节)
createor replace type vartabletype as table of varchar2(1000);
然后创建两个相关的函数
数字列表函数
createor replace function str2numList( p_string in varchar2 ) return numTableType
as
v_str long default p_string || ',';
v_n number;
v_data numTableType := numTableType();
begin
loop
v_n := to_number(instr( v_str, ',' ));
exit when (nvl(v_n,0) = 0);
v_data.extend;
v_data( v_data.count ) := ltrim(rtrim(substr(v_str,1,v_n-1)));
v_str := substr( v_str, v_n+1 );
end loop;
return v_data;
end;
字符列表函数
createor replace function str2varList( p_string in varchar2 ) return VarTableType
as
v_str long default p_string || ',';
v_n varchar2(2000);
v_data VarTableType := VarTableType();
begin
loop
v_n :=instr( v_str, ',' );
exit when (nvl(v_n,0) = 0);
v_data.extend;
v_data( v_data.count ) := ltrim(rtrim(substr(v_str,1,v_n-1)));
v_str := substr( v_str, v_n+1 );
end loop;
return v_data;
end;
创建之后,我们就可以采用如下的方式来使用in list的绑定了。如可以采用如下的三种方案
SELECT/*+ ordered use_nl(a,u) */id, user_id, BITAND(promoted_type,4) busauth
from table(STR2NUMLIST(:bind0)) a,
bmw_users u
where u.user_id = a.column_value
SELECT/*+ leading(a) */id, user_id, BITAND(promoted_type,4) busauth
from bmw_users u where user_id in
(select * from table(STR2NUMLIST(:bind0)) a);
SELECT/*+ index(bmw_users UK_BMW_USERS_USERID) */id, user_id
from bmw_users where user_id in
(SELECT * FROM THE (SELECT CAST(STR2NUMLIST(:bind0) AS NUMTABLETYPE) FROM dual) WHERE rownum<1000)
在如上的方案中,以上语句中的hint提示,是为了稳定执行计划,防止Oracle对in list的错误估计而导致走hash连接。一般建议采用第一种方法,比较简单可靠并且可以指定稳定的计划。但是要求数据库的版本比较高,在老版本中(8i),可能只能采用第三种方法。总的来说,1、2两种方法比3要少6个逻辑读左右。如:
SQL> SELECT /*+ ordered use_nl(a,u) */ id, user_id
2from table(STR2NUMLIST('1,2,3')) a,
3bmw_users u
4*where u.user_id = a.column_value
Execution Plan
----------------------------------------------------------
0SELECT STATEMENT Optimizer=CHOOSE (Cost=3279 Card=8168 Bytes =334888)
10NESTED LOOPS (Cost=3279 Card=8168 Bytes=334888)
21COLLECTION ITERATOR (PICKLER FETCH) OF 'STR2NUMLIST'
31TABLE ACCESS (BY INDEX ROWID) OF 'BMW_USERS' (Cost=1 Card=1 Bytes=39)
43INDEX (UNIQUE SCAN) OF 'UK_BMW_USERS_USERID' (UNIQUE)
Statistics
----------------------------------------------------------
0recursive calls
0db block gets
10consistent gets
0physical reads
0redo size
......
SQL> SELECT/*+ index(bmw_users UK_BMW_USERS_USERID) */ id, user_id
2from bmw_users where user_id in
3*(SELECT * FROM THE (SELECT CAST(STR2NUMLIST('1,2,3') AS NUMTABLETYPE) FROM dual) WHERE rownum<1000)
Execution Plan
----------------------------------------------------------
0SELECT STATEMENT Optimizer=CHOOSE (Cost=430 Card=999 Bytes=51948)
10NESTED LOOPS (Cost=430 Card=999 Bytes=51948)
21VIEW OF 'VW_NSO_1' (Cost=11 Card=999 Bytes=12987)
32SORT (UNIQUE)
43COUNT (STOPKEY)
54COLLECTION ITERATOR (PICKLER FETCH) OF 'STR2NUMLIST'
65TABLE ACCESS (FULL) OF 'DUAL' (Cost=2 Card=82)
71TABLE ACCESS (BY INDEX ROWID) OF 'BMW_USERS' (Cost=1 Card=1 Bytes=39)
87INDEX (UNIQUE SCAN) OF 'UK_BMW_USERS_USERID' (UNIQUE)
Statistics
----------------------------------------------------------
0recursive calls
0db block gets
16consistent gets
0physical reads
0redo size
ORDERED好理解,就是表示根据 from 后面表的顺序join,从左到右,左边的表做驱动表
USE_NL(),先看看
oracle doc怎么说:
In this statement, the USE_NL hint explicitly chooses a
nested loops join with the customers table as the inner table:
SELECT
/*+ ORDERED USE_NL(customers) to get first row faster */
accounts.balance,
customers.last_name, customers.first_name
FROM accounts, customers
WHERE
accounts.customer_id = customers.customer_id;
customers 作为inner
table,也就是说作为被驱动表。驱动表称为outer table。
也就是说use_nl如果只带了一个表名作为参数,则该表为被驱动
表。
如果带了2个以上的参数,oracle 并没有指出 use_nl(a b) 中 哪个是驱动表,所以常使用 ordered 或者
full() 或者 index() 来强化我们的目标
oracle numlist,oracle sql str2numlist numtabletype相关推荐
- 监控Oracle性能的SQL
监控Oracle性能的SQL 1. 监控事例的等待 select event,sum(decode(wait_Time,0,0,1)) "Prev", sum(dec ...
- 利用迁移助手从Oracle迁移到SQL Server
在实际的项目中,我们常常需要在不同的数据库之前进行迁移,在以前,这可能是和麻烦的事情,但是现在有很多的好的工具可以快速的帮助我们忙成这个目标. 下面我们从来看看如何从Oracle迁移到SQL Serv ...
- oracle导入dmp报无效的sql,oracle施用pl/sql导入数据库备份文件dmp导入失败原因
oracle使用pl/sql导入数据库备份文件dmp导入失败原因 利用PL/SQL导入数据库备份失败: Tools→Import →Tables Import Executable选择导入工具路径 D ...
- 判断题:oracle自带的sql语言环境是pl/sql,Oracle之PL/SQL学习笔记之数据类型(三)
Oracle之PL/SQL学习笔记之数据类型(三) 所有的编程语言中变量是使用最频繁的.PL/SQL作为一个面向过程的数据库编程语言同样少不了变量,利用变量可以把PL/SQL块需要的参数传递进来,做到 ...
- 使用navicat premium将数据库从Oracle迁移到SQL Server,或从Oracle迁移到MySQL
有时候我们有迁移数据库的需求,例如从Oracle迁移到SQL Server,或者从MySQL迁移到Oracle. 很多江湖好汉一时不知如何手工操作,所幸的是Navicat提供了迁移的自动化操作界面. ...
- Oracle的PL/SQL编程前奏之基础技能实战一(匿名子程序)
Oracle的PL/SQL编程之基础技能实战一 一>基础代码检查检查以bm_开头的系统初始化编码表是否有空值.与业务系统相关的编码项不能存在空值,会导致系统业务无法办理.为初始化数据表.在做测试 ...
- oracle怎么设置sql每隔一段时间执行一次_Oracle大规模数据快速导出文本文件
哈喽,前几久,和大家分享过如何把文本数据快速导入数据库(点击即可打开),今天再和大家分享一个小技能,将Oracle数据库中的数据按照指定分割符.指定字段导出至文本文件. 首先来张图,看看导出的数据是什 ...
- 【oracle】oracle经典sql,exception,database link纠错
[oracle]oracle经典sql,exception,database link纠错 1111-01 oracle经典sql,exception,database link纠错 1.给表tabl ...
- Oracle临时表和SQL Server临时表的不同点对比
文章来源:http://www.codesky.net/article/201109/141401.html 1.简介 Oracle数据库除了可以保存永久表外,还可以建立临时表temporary ta ...
最新文章
- 文字描边_学会这种描边效果,你的PPT也能这么好看
- php转译html,使用php转义输出HTML到JavaScript
- 音视频播放、录音、拍照
- 谷歌浏览器登录不了账号_谷歌浏览器使用分享(可谷歌账号登录)之谷歌账号登录...
- 树形DP(简单题)(Y HDU4705)
- 服务器来电后自动开机|xfs文进系统备份恢复linux下误删除的文件
- POJ 3264 -----RMQ问题
- 安卓控件显示等宽字体的办法
- cad老是弹出命令中发生异常_CAD为什么会异常退出?遇到CAD异常退出怎么办-百度经验...
- QT软件ICON图标在线制作
- 家庭和睦、人生平淡也是一种成功
- 【ubuntu】解决 Certificate verification failed: The certificate is NOT trusted
- java 打印jpg、pdf、word
- pinyin4j:拼音与汉字的转换实例
- C语言中的void和void*的定义及用法
- 2018,ANG发展峰会惊喜来袭
- 基于HTML电商购物项目的设计与实现——html+css+javascript+jquery+bootstarp响应式图书商城
- 定点补码运算c语言,单选(3分) 下列关于补码定点运算的描述中,错误的是( )...
- 大学生学计算机打字速度,小学生计算机打字速度研究报告
- 线性表的链式存储结构以及单链表的插入和删除原理实现
热门文章
- 【报告分享】中国“新基建”发展研究报告.pdf(附下载链接)
- Make GNN Great Again: GNN 上的预训练和自监督学习
- 自然语言处理之TF-IDF
- # 异运算_一年级数学:3000道20内纯进、退位口算题,每天100道日新又月异
- 使用python排序_Python排序
- 什么是智慧仓储化管理系统?
- 平台卖家要不要做独立站?
- linux实现单机qq_Linux后台服务器开发——Linux下进程间通信的方式有哪些?
- 吴恩达深度学习之四《卷积神经网络》学习笔记
- 集成学习——XGBoost原理理解