SQL基础
来源:互联网 发布:国联证券交易软件 编辑:程序博客网 时间:2024/05/03 03:50
escape 定义转义字符
SQL> select * from test;
TEST
--------------------
sdd_kk
d'd
dfsfsa
dffa%asfs
12345
1%2345
1%54321
2%54321
%%54321
A&B
已选择9行。
SQL> select * from test where test like 'sdd\_%' escape '\';
TEST
--------------------
sdd_kk
转义字符为'\';
SQL> select * from test where test like 'sdd=_%' escape '=';
TEST
--------------------
sdd_kk
转义字符为'=';
SQL> select * from test where test like 'sddd_%' escape 'd';
未选定行
转义字符为d,没有实现转义功能;
但是'&'不能通过转义字符查找:
SQL> select * from test where test like '%\&%' escape'\';
select * from test where test like '%\&%' escape'\'
*
第 1 行出现错误:
ORA-01424: 转义符之后字符缺失或非法
可以通过另外的方式进行转义:
SQL> select ascii('&') from dual;
ASCII('&')
----------
38
SQL> select * from test where test like '%'||chr(38)||'%';
TEST
--------------------
A&B
' 的转义:
SQL> select * from test where test like '%''%';
TEST
--------------------
d'd
特殊符号的数据的插入
SQL> insert into test values('test&test');输入 test 的值: test原值 1: insert into test values('test&test')新值 1: insert into test values('testtest') -虽然插入,但是数据不对。已创建 1 行。SQL> show definedefine "&" (hex 26)SQL> set define offSQL> show definedefine OFFSQL> insert into test values('test&test');已创建 1 行。SQL> show escapeescape OFFSQL> set escape onSQL> show escapeescape "\" (hex 5c)SQL> insert into test values('test\&test');已创建 1 行。SQL> select * from test;TEST--------------------sdd_kkd'ddfsfsadffa%asfs123451%23451%543212%54321%%54321A&BtesttestTEST--------------------test&testtest&test已选择13行。SQL> commit;提交完成。SQL> select * from test;TEST--------------------sdd_kkd'ddfsfsadffa%asfs123451%23451%543212%54321%%54321A&BtesttestTEST--------------------test&testtest&test已选择13行。SQL> insert into test values('test\%test');已创建 1 行。SQL> insert into test values('test\_test');已创建 1 行。SQL> insert into test values('test\'test);insert into test values('test'test) *第 1 行出现错误:ORA-00917: 缺失逗号SQL> insert into test values('test''test');已创建 1 行。SQL> select * from test;TEST--------------------sdd_kkd'ddfsfsadffa%asfs123451%23451%543212%54321%%54321A&BtesttestTEST--------------------test&testtest&testtest%testtest_testtest'test已选择16行。
连接符‘||’导致了新一轮的转义:连接符号‘||’左右的单引号没有任何的关系,除非‘||’是作为字符串的一部分(这在动态SQL中很常见)。
SQL> SELECT 'ORACLE'||'''' FROM DUAL;
'ORACLE'||''
----------
ORACLE'
个人理解,'ORACLE'||'''' 后面的“''''”应该认为是一个字符串(即前后单引号,中间是“''”串,而中间又是密集单引号,因此第一个为转义功能)
SQL> SELECT 'ORACLE''''' FROM DUAL;
'ORACLE'''''
------------
ORACLE''
对于第一个,前两个单引号配对,后面四个单引号按照上面的第一条原则分配,既:SELECT 'ORACLE'||'''' FROM DUAL;
对于第二个,由于第二个单引号后面存在单引号,所以就不与第一个配对,而是充当了转义的角色。既:SELECT 'ORACLE''''' FROM DUAL;
注意:如果是 '/' 作为检索字符, 必须 用 '/' 作为转义符, 正斜扛也一样.
- select * from wan_test where psid like '%//%' escape '/'
exist 和in的效率比较
一直以来认为exists比in效率高的说法是不准确的。
如果两个表中一个较小,一个是大表,则子查询表大的用exists,子查询表小的用in:
例如:表A(小表),表B(大表)
1:
select * from A where cc in (select cc from B)
select * from A where exists(select cc from B where cc=A.cc)
2:
select * from B where cc in (select cc from A)
select * from B where exists(select cc from A where cc=B.cc)
带in的关联子查询是多余的,因为in子句和子查询中相关的操作的功能是一样的。如:
select staff_name from staff_member where staff_id in
(select staff_id from staff_func where staff_member.staff_id=staff_func.staff_id);
为非关联子查询指定exists子句是不适当的,因为这样会产生笛卡乘积。如:
select staff_name from staff_member where staff_id
exists (select staff_id from staff_func);
not in 和not exists
如果查询语句使用了not in 那么内外表都进行全表扫描,没有用到索引;
而not extsts 的子查询依然能用到表上的索引。
所以无论哪个表大,用not exists都比not in要快。
尽量不要使用not in子句。使用minus 子句都比not in 子句快,虽然使用minus子句要进行两次查询:
select staff_name from staff_member where staff_id in (select staff_id from staff_member minus select staff_id from staff_func where func_id like '81%');
in 与 "=" 的区别
select name from student where name in ('zhang','wang','li','zhao');
与
select name from student where name='zhang' or name='li' or name='wang' or name='zhao'
的结果是相同的。
有两个简单例子,以说明 “exists”和“in”的效率问题
1) select * from T1 where exists(select * from T2 where T1.a=T2.a) ;
T1数据量小而T2数据量非常大时,T1<<T2 时,1) 的查询效率高。
2) select * from T1 where T1.a in (select T2.a from T2) ;
T1数据量非常大而T2数据量小时,T1>>T2 时,2) 的查询效率高。
---------------------------------------------------------------
今天市场报告有个sql及慢,运行需要20多分钟,如下:
update p_container_decl cd
set cd.ANNUL_FLAG=\'0001\',ANNUL_DATE = sysdate
where exists(
select 1
from (
select tc.decl_no,tc.goods_no
from p_transfer_cont tc,P_AFFIRM_DO ad
where tc.GOODS_DECL_NO = ad.DECL_NO
and ad.DECL_NO = \'sssssssssssssssss\'
) a
where a.decl_no = cd.decl_no
and a.goods_no = cd.goods_no
)
上面涉及的3个表的记录数都不小,均在百万左右。根据这种情况,我想到了前不久看的tom的一篇文章,说的是exists和in的区别,in 是把外表和那表作hash join,而exists是对外表作loop,每次loop再对那表进行查询。
这样的话,in适合内外表都很大的情况,exists适合外表结果集很小的情况。
而我目前的情况适合用in来作查询,于是我改写了sql,如下:
update p_container_decl cd
set cd.ANNUL_FLAG=\'0001\',ANNUL_DATE = sysdate
where (decl_no,goods_no) in
(
select tc.decl_no,tc.goods_no
from p_transfer_cont tc,P_AFFIRM_DO ad
where tc.GOODS_DECL_NO = ad.DECL_NO
and ad.DECL_NO = ‘ssssssssssss’
)
让市场人员测试,结果运行时间在1分钟内。问题解决了,看来exists和in确实是要根据表的数据量来决定使用。
--------------------------------------------------------------------------
select 1 from ... sql语句中的1代表什么意思?
select 1 from ..., sql语句中的1代表什么意思?查出来是个什么结果?
select 1 from table;与select anycol(目的表集合中的任意一行) from table;与select * from table 从作用上来说是没有差别的,都是查看是否有记录,一般是作条件查询用的。select 1 from 中的1是一常量(可以为任意数值),查到的所有行的值都是它,但从效率上来说,1>anycol>*,因为不用查字典表。
测试场景:(转自网络文献)
table表是一个数据表,假设表的行数为10行。
1:select 1 from table 增加临时列,每行的列值是写在select后的数,这条sql语句中是1
2:select count(1) from table 管count(a)的a值如何变化,得出的值总是table表的行数
3:select sum(1) from table 计算临时列的和
1* select 1 from emp where empno=7369 or empno=7499scott@WENCHAOD> / 1---------- 1 1----
exist实例:
例1:
让我们在一个简单的例子。下面是一个使用EXISTS条件的SQL语句,:
SELECT *
FROM suppliers
WHERE EXISTS
(select *
from orders
where suppliers.supplier_id = orders.supplier_id);
这个SELECT语句将返回供应商表中与订单表中至少有一条记录是supplier_id相同的的供应商信息。
例2 – NOT EXISTS
EXISTS 条件也可以与NOT运算符结合。
For example,
SELECT *
FROM suppliers
WHERE not exists (select * from orders Where suppliers.supplier_id = orders.supplier_id);
USE pubs GO SELECT DISTINCT pub_name FROM publishers WHERE EXISTS (SELECT * FROM titles WHERE pub_id = publishers.pub_id AND type = 'business') GO -- Or, using the IN clause: USE pubs GO SELECT distinct pub_name FROM publishers WHERE pub_id IN (SELECT pub_id FROM titles WHERE type = 'business') GO
in的SQL语句SELECT id, category_id, htmlfile, title, convert(varchar(20),begintime,112) as pubtime FROM tab_oa_pub WHERE is_check=1 and category_id in (select id from tab_oa_pub_cate where no='1') order by begintime desc修改为exists的SQL语句SELECT id, category_id, htmlfile, title, convert(varchar(20),begintime,112) as pubtime FROM tab_oa_pub WHERE is_check=1 and exists (select id from tab_oa_pub_cate where tab_oa_pub.category_id=convert(int,no) and no='1') order by begintime desc
http://alfredgao.iteye.com/blog/244144
- SQL基础
- SQL基础
- SQL基础
- SQL 基础
- sql:基础
- SQL基础
- SQL基础
- SQL基础
- SQL基础
- SQL基础
- SQL 基础
- sql基础
- SQL基础
- sql基础
- SQL基础
- SQL基础
- sql 基础
- sql基础
- CentOS yum安装wine
- 着眼移动端广告的新未来,Google尝试Deep Link技术
- Javascript绝句欣赏
- C++中STL常用容器的区别
- UVa 10911 Forming Quiz Teams / 状态压缩DP
- SQL基础
- 关于0xAA和0x55
- 月光博客的发展历程
- cocos2d::Map< K,V > cocos2dx 3.0
- ORA-16072: a minimum of one standby database destination is required
- Linux查找常用 :grep find,linux 查找 文件名字 带字符串的文件,查找含有字符的文件
- inux下检测U盘插入并读取文件
- 第二学期第三周项目2--旱冰场造价
- ngui字体 BMFont中文字体图集制作的方法~(for unity ngui)