1、尽量减少子查询,可以改成left join这种方式
2、建立合适的索引
3、尽量避免使用游标,超过1万条尽量改成其他方式
4、拆分)(水平和垂直拆分)
5、sql执行顺序
先执行from关键字后面的语句,明确数据的来源,它是从哪张表取来的。
接着执行where关键字后面的语句,对数据进行筛选。
再接着执行group by后面的语句,对数据进行分组分类。
然后执行select后面的语句,也就是对处理好的数据,具体要取哪一部分。
最后执行order by后面的语句,对最终的结果进行排序。
where后面的条件从后往前执行,过滤掉最大数据的条件放在最后
----------------------------------------------------------------------------
1、如果是上千万的两张表,千万别用left join这种,查询太慢
可以用java代码先查询出来一张表,获取数据,再去查询另一张表,逻辑用java代码操作,这种会快很多
2、可以查询出来 sql 慢查询,比如>0.03的sql,在优化这些sql语句
in、like、索引
3、查询执行慢的SQL
--执行慢的SQL:
SELECT S.SQL_TEXT,
S.SQL_FULLTEXT,
S.SQL_ID,
ROUND(ELAPSED_TIME / 1000000 / (CASE
WHEN (EXECUTIONS = 0 OR NVL(EXECUTIONS, 1 ) = 1) THEN
1
ELSE
EXECUTIONS
END),
2) "执行时间'S'",
S.EXECUTIONS "执行次数",
S.OPTIMIZER_COST "COST",
S.SORTS,
S.MODULE, --连接模式(JDBC THIN CLIENT:程序)
-- S.LOCKED_TOTAL,
S.PHYSICAL_READ_BYTES "物理读",
-- S.PHYSICAL_READ_REQUESTS "物理读请求",
S.PHYSICAL_WRITE_REQUESTS "物理写",
-- S.PHYSICAL_WRITE_BYTES "物理写请求",
S.ROWS_PROCESSED "返回行数",
S.DISK_READS "磁盘读",
S.DIRECT_WRITES "直接路径写",
S.PARSING_SCHEMA_NAME,
S.LAST_ACTIVE_TIME
FROM GV$SQLAREA S
WHERE ROUND(ELAPSED_TIME / 1000000 / (CASE
WHEN (EXECUTIONS = 0 OR NVL(EXECUTIONS, 1 ) = 1) THEN
1
ELSE
EXECUTIONS
END),
2) > 5 --100 0000微秒=1S
AND S.PARSING_SCHEMA_NAME = USER
AND TO_CHAR(S.LAST_LOAD_TIME, 'YYYY-MM-DD') =
TO_CHAR( SYSDATE, 'YYYY-MM-DD' )
AND S.COMMAND_TYPE IN (2 , 3, 5, 6 , 189)
ORDER BY "执行时间'S'" DESC;
/* SQL中 COMMAND_TYPE意义:
2:INSERT
3:SELECT
6:UPDATE
7:DELETE
189:MERGE