SQL杂项

一、多表联合查询

典型语句
SELECT R.READER_NAME, B.BOOK_NAME, BL.LEND_DATE
FROM READERS R, BOOKS B, BOOK_LEND BL
WHERE R.READER_ID = BL.READER_ID
AND B.ISBN = BL.ISBN
AND BL.RETURN_DATE IS NULL

不要忘记where子句中表的条件联合,避免笛卡尔结果集的产生
表的条件联合时,返回行数最小的表将作为基表,其他表和基表进行条件联合
请为表指定别名,增加可读性,提高SQL解析效率
大多数情况下,联合查询都是等值联合,不等值联合的意义不大

内联合 join on / inner join on
         from table1 t1 join table2 t2 on t1.id = t2.id
左向外联合 left join on
from table1 t1 left join table2 t2 on t1.id = t2.id
右向外联合 right join on
from table1 t1 right join table2 t2 on t1.id = t2.id
完整外联合 full join on
from table1 t1 full join table2 t2 on t1.id = t2.id
自我联合
           from table1 a, table1 b where a.id = b.id

使用等于条件时,子查询中的返回结果需要唯一
select * from tb_card where kh = (select kh from tb_zh_card where zhh = '00001233');
Exist 子查询中有记录时返回true
select * from tb_zh a where exists (select 1 from tb_dbdj_jyjl b where b.zhh = a.zhh)
Any 子查询中任意一条记录符合条件时返回true
select name from orders where name > any (select name from orders where name = 'JACKS BIKE');
All 子查询中的所有记录都符合条件时返回true
select name from orders where name <> all (select name from orders where name = 'JACKS BIKE');

复合子查询
select * from tb_zh where (zhh, sfzh) in (select zhh, sfzh from tb_dbdj_jyjl);

Inline view
select a.name from (select * from tb_dic_yljg) a , (select * from tb_dbdj_jyjl) b where a.hospital_id = b.yydm;

Select list
select (select name from tb_dic_yljg where hospital_id = a.yydm) from tb_dbdj_jyjl a;

union - 返回两个查询结果的并集,并去除其中的重复部分
select name from table1 union select name from table2;
union all - 返回两个查询结果的并集,不去除其中的重复部分
select name from table1 union all select name from table2;
intersect – 返回两个查询结果的交集
select name from table1 intersect select name from table2;
minus – 返回存在于第一个查询结果,但不存在于第二个查询结果的记录
select name from table1 minus select name from table2;

二、SQL优化

少使用select *,尽量只查询需要使用的字段
数据库会将‘*’转换为所有的列名,这个工作是通过查询数据字典完成的,这意味着将耗费更多的时间
尽量只查询需要使用的字段,尤其在表中存在大文本或大二进制对象时
多表查询时,请使用表的别名
当在SQL语句中连接多个表时,请使用表的别名并把别名前缀于每个Column上。这样一来,就可以减少解析的时间并减少那些由Column歧义引起的语法错误
当SQL条件中使用多个OR时,如果可能,可以改成IN,IN的效率更高一些

尽量在where条件中进行条件限制,将符合条件的查询结果集控制在最小
不要滥用排序
排序语句在数据库内存中进行,如果内存排序空间占满,就在硬盘上排序
以下语句会自动执行排序操作
order by 子句
group by 子句
select distinct
集合语句union、intersect、minus,union all不排序
创建索引
优化器调用sort merge join操作

sequence/identity/serial等数据库自增长类型,都是由数据库事务来管理的,一旦表的新增数据并发量很高,主键值的生成可能成为性能瓶颈
uuid是高效的主键生成方式,它不是数据库管理的。新增记录并发量高时效率很高,查询效率不如数字型
慎用hibernate中的increment(又名vm)主键生成方式,在负载均衡环境下,会存在致命的主键冲突问题


三、事务

1、事务的基本特征
Atomic(原子性)
事务中包含的操作被看做一个逻辑单元,这个逻辑单元中的操作要么全部成功,要么全部失败
Consistency(一致性)
只有合法的数据可以被写入数据库,否则事务应该将其回滚到最初状态
Isolation(隔离性)
事务允许多个用户对同一个数据进行并发访问,而不破坏数据的正确性和完整性。同时,并行事务的修改必须与其他并行事务的修改相互独立
Durability(持久性)
事务结束后,事务处理的结果必须能够得到固化

2、事务隔离级别
Read Uncommitted (未提交读)
事务隔离的最低级别
不允许更新丢失,如果一个事务已经开始写数据,则另外一个数据不允许同时进行写操作
允许脏读,允许读取已经被其它事务修改但尚未提交确定的数据
Read Committed(提交读)
不允许脏读,读取数据的事务允许其他事务继续访问该行数据,未提交写事务将会禁止其他事务访问该行
允许不可重复读取,一个事务对同一行数据重复读取两次,可能会得到了不同的结果
Repeatable Read(可重复读取)
禁止不可重复读取和脏读取,读取数据事务将会禁止写事务(但允许读事务),写事务则禁止任何其他事务
有时可能出现幻影数据,事务在操作过程中进行两次查询,第二次查询的结果包含了第一次查询中未出现的数据
Serializable(序列化)
事务隔离的最高级别
要求事务序列化执行,事务只能一个接着一个地执行,不能并发执行
事务之间完全隔离


你可能感兴趣的:(sql,工作,Hibernate)