SQL业务审核与优化
- 类似与code review
- 评审业务Schema和SQL设计
- 偏重关注性能
- 是业务优化的主要入口之一
- 表和字段命名是否合规
- 字段类型,长度设计是否适当
- 表关联关系是否合理
- 主键,更新时间保留字段等是否符合要求
- 约束,默认值等配置是否恰当
- 了解业务,表数据量,增长模式
- 数据访问模式,均衡度
- 根据业务需求,表是否需要分区,是否有数据什么周期
- SQL语句的执行频率
- 表上是否有合适的索引
- 单次执行的成本
- 执行模式,锁情况分析
- 关注事务上下文
- 业务开发阶段,上线前
- 业务版本变更,线上更新前
- 新表和SQL上线
- SQL查询条件变化
- SQL查询频率变化
- 业务逻辑导致现有表数据量规模变化
- SQL审核需要开发与应用运维支持
- 充分沟通,做好必要性说明和教育工作
- 指定业务发布流程,嵌入DBA审核环节
- 积累经验,不断完善评审方法
- 确认应用程序是否向数据库请求了大量超过需要的数据
- 确认mysql服务器层是否在处理大量超过需要的数据记录
- 查询不需要的记录
- 多表关联时返回全部列
- 总是取出全部列
- 重复查询相同的数据
- 响应时间
- 扫描的行数
- 返回的行数
- 使用索引覆盖扫描,把所有需要用的列都放到索引中。
- 改变库表结构。例如使用单独的汇总表
- 重写这个复杂的查询,让mysql优化器能够以更优化的方式执行这个查询。
- 客服端发送一条查询给服务器
- 服务器先检查缓存。如果命中缓存,则立刻返回结果。否则进入下一阶段。
- 服务器端进行SQL解析,预处理,再由优化器生成对应的执行计划。
- mysql根据优化器生成的执行计划,调用存储引擎的API来执行查询。
- 将结果返回给客户端
mysql> show full processlist;
+----+------+-----------+--------+---------+------+-------+------------------------+
| Id | User | Host | db | Command | Time | State | Info |
+----+------+-----------+--------+---------+------+-------+------------------------+
| 39 | root | localhost | sakila | Sleep | 4 | | NULL |
| 40 | root | localhost | sakila | Query | 0 | NULL | show full processlist |
+----+------+-----------+--------+---------+------+-------+------------------------+
2 rows in set (0.00 sec)
mysql> select count(*) from film_actor;
+----------+
| count(*) |
+----------+
| 5462 |
+----------+
1 row in set (0.00 sec) mysql> show status like 'last_query_cost';
+-----------------+-------------+
| Variable_name | Value |
+-----------------+-------------+
| Last_query_cost | 1040.599000 |
+-----------------+-------------+
- 统计信息不准确
- 执行计划中的成本估算不等同于实际执行的成本。
- 有的计划虽然要读取更多页,但是这些页在缓存中。
- mysql的最有可能和你想的最优不一样。
- 比如你希望执行时间尽可能的短,而mysql只是基于成本模型选择的最优执行计划。
- mysql从不考虑其他并发执行的查询,这可能会影响到当前查询速度。
- mysql不会考虑不受其控制的操作的成本。
- 如执行存储过程或者用户自定义函数的成本
- 静态优化
- 直接对解析树进行分析,并完成优化。优化器通过一些简单的代数变换将where条件转换成另一种等价形式。静态优化在第一次完成后一直有效。可以认为这是一种"编译时优化"
- 动态优化
- 动态优化和查询的上下文有关。也和其他很多因素有关,例如where中的取值,索引中条目,等等。每次查询的时候都重新评估,可以认为这是一种"运行时优化"
- 重新定义关联表的顺序。
- 将外联结转成内连接
- 使用等价变化规则
- 合并和减少一些比较,移除一些恒成立和一些恒不成立的判断
- 优化count(),min(),max(),min()就直接拿BTree树最左端数据行
- 预估并转换为常数表达式
- 覆盖索引扫描
- 子查询优化
- 提前终止查询
- 等值传播
mysql> select * from film where film_id in ( select film_id from film_actor where actor_id =1) \G;
select * from film where film_id in (1,23,25,106,140);
mysql> explain select * from film f inner join film_actor fa where f.film_id=fa.film_id and actor_id =1;
+----+-------------+-------+--------+------------------------+---------+---------+-------------------+------+-------+
| id | select_type | table | type | possible_keys | key | key_len | ref | rows | Extra |
+----+-------------+-------+--------+------------------------+---------+---------+-------------------+------+-------+
| 1 | SIMPLE | fa | ref | PRIMARY,idx_fk_film_id | PRIMARY | 2 | const | 19 | |
| 1 | SIMPLE | f | eq_ref | PRIMARY | PRIMARY | 2 | sakila.fa.film_id | 1 | |
+----+-------------+-------+--------+------------------------+---------+---------+-------------------+------+-------+
2 rows in set (0.00 sec)
(select first_name,last_name
from sakila.actor
order by last_name)
union all
(select first_name,last_name
from sakila.customer
order by last_name)
limit 20;
(select first_name,last_name
from sakila.actor
order by last_name
limit 20)
union all
(select first_name,last_name
from sakila.customer
order by last_name
limit 20)
limit 20;
现在中间的临时表中只会包含40条记录。
mysql> explain select min(actor_id) from actor where first_name='PENELOPE';
+----+-------------+-------+------+---------------+------+---------+------+------+-------------+
| id | select_type | table | type | possible_keys | key | key_len | ref | rows | Extra |
+----+-------------+-------+------+---------------+------+---------+------+------+-------------+
| 1 | SIMPLE | actor | ALL | NULL | NULL | NULL | NULL | 200 | Using where |
+----+-------------+-------+------+---------------+------+---------+------+------+-------------+
1 row in set (0.00 sec)
mysql> explain select actor_id from actor USE INDEX(PRIMARY) where first_name='PENELOPE' LIMIT 1;
+----+-------------+-------+------+---------------+------+---------+------+------+-------------+
| id | select_type | table | type | possible_keys | key | key_len | ref | rows | Extra |
+----+-------------+-------+------+---------------+------+---------+------+------+-------------+
| 1 | SIMPLE | actor | ALL | NULL | NULL | NULL | NULL | 200 | Using where |
+----+-------------+-------+------+---------------+------+---------+------+------+-------------+
1 row in set (0.00 sec)
mysql> update tbl AS outer_tbl
set cnt = (
select count(*) from tbl AS inner_tbl
where inner_tbl.type = outer_tbl.type
);
error:you can't specify target table 'outer_tbl' for update in from clause
mysql> update tbl
inner join (
select type,count(*) AS cnt
from tbl
group by type
)AS der using(type)
set tbl.cnt = der.cnt;
- HIGH_PRIORITY,LOW_PRIORITY
- 这个提示告诉mysql,当多个语句同时访问某一个表的时候,哪些语句的优先级相对高些,哪些语句的优先级相对低些。
- 只对使用表锁的存储引擎有效,不要在innodb或者其他有细粒度锁机制和并发控制的引擎中使用。
- DELAYED
- 这个提示对insert,replace有效。mysql会将使用该提示的语句立即返回给客户端,并将插入的行数据放入到缓冲区,然后在表空间时批量将数据写入。
- 日志系统使用这样的提示非常有效,或者是其他需要写入大量数据但是客户端却不需要等待单条语句完成I/O的应用。这个用法有一些限制:并不是所有的存储引擎都支持这样的做法;并且该提示会导致函数LAST_INSERT_ID无法正常工作。
- USE INDEX,IGNORE INDEX ,FORCE INDEX
mysql> show status like 'com%';
+---------------------------+-------+
| Variable_name | Value |
+---------------------------+-------+
| Com_admin_commands | 0 |
| Com_assign_to_keycache | 0 |
| Com_alter_db | 0 |
| Com_alter_procedure | 0 |
| Com_alter_server | 0 |
| Com_alter_table | 0 |
- 慢查询日志,定位低效SQL;long_query_time,慢查询的标准时间;
- 慢查询是,查询结束之后才记录;因此他不是实时的;show processlist 查看mysql在进行的线程,查看线程的一些状态,可以实时地查看SQL的执行情况;
mysql> explain select b from t where a =1;
+----+-------------+-------+------+---------------+------+---------+-------+------+-------------+
| id | select_type | table | type | possible_keys | key | key_len | ref | rows | Extra |
+----+-------------+-------+------+---------------+------+---------+-------+------+-------------+
| 1 | SIMPLE | t | ref | a | a | 5 | const | 1 | Using where |
+----+-------------+-------+------+---------------+------+---------+-------+------+-------------+
1 row in set (0.00 sec)
- select_type
- simple:简单表,即不使用表链接或者子查询
- Primary:主查询,即外层的查询
- union:union中的第二个或者后面的查询语句
- subquery: 子查询中的第一个select
- table:输出结果集的表
- type:访问类型
- all,全表扫描
- index,索引全扫描
- range,索引范围扫描,常见于< , >,between
- ref,使用非唯一索引扫描或唯一索引的前缀扫描,返回匹配某个单独值的记录行
- eq_ref,类似ref,区别在于使用了唯一索引;
- const/system,表中最多有一个匹配行;Primary key 或 unique index;
- null,不用访问表或者索引就可以得到结果
- possible_keys:表示查询时可能使用的索引
- key: 表示实际使用的索引
- key_len: 使用到索引字段的长度
- rows:扫描行的数量
- extra:执行情况的说明和描述;
mysql> select @@have_profiling;
+------------------+
| @@have_profiling |
+------------------+
| YES |
+------------------+
mysql> select @@profiling;
+-------------+
| @@profiling |
+-------------+
| 0 |
+-------------+
1 row in set (0.00 sec)
mysql> set profiling=1;
Query OK, 0 rows affected (0.00 sec)
mysql> select count(*) from payment;
+----------+
| count(*) |
+----------+
| 16049 |
+----------+
1 row in set (0.02 sec)
mysql> show profiles;
+----------+------------+------------------------------+
| Query_ID | Duration | Query |
+----------+------------+------------------------------+
| 1 | 0.01064275 | select count(*) from payment |
| 2 | 0.00048225 | show databases |
| 3 | 0.00015000 | show DATABASE() |
| 4 | 0.00039975 | show tables |
+----------+------------+------------------------------+
mysql> show profile for query 4;
+----------------------+----------+
| Status | Duration |
+----------------------+----------+
| starting | 0.000058 |
| checking permissions | 0.000009 |
| Opening tables | 0.000050 |
| System lock | 0.000008 |
| init | 0.000012 |
| optimizing | 0.000005 |
| statistics | 0.000012 |
| preparing | 0.000010 |
| executing | 0.000007 |
| checking permissions | 0.000132 |
| Sending data | 0.000042 |
| end | 0.000007 |
| query end | 0.000007 |
| closing tables | 0.000005 |
| removing tmp table | 0.000009 |
| closing tables | 0.000006 |
| freeing items | 0.000015 |
| logging slow query | 0.000005 |
| cleaning up | 0.000006 |
+----------------------+----------+
19 rows in set (0.00 sec)
mysql> show profile cpu for query 4;
+----------------------+----------+----------+------------+
| Status | Duration | CPU_user | CPU_system |
+----------------------+----------+----------+------------+
| starting | 0.000058 | 0.000000 | 0.000000 |
| checking permissions | 0.000009 | 0.000000 | 0.000000 |
| Opening tables | 0.000050 | 0.000000 | 0.000000 |
| System lock | 0.000008 | 0.000000 | 0.000000 |
| init | 0.000012 | 0.000000 | 0.000000 |
| optimizing | 0.000005 | 0.000000 | 0.000000 |
| statistics | 0.000012 | 0.000000 | 0.000000 |
| preparing | 0.000010 | 0.000000 | 0.000000 |
| executing | 0.000007 | 0.000000 | 0.000000 |
| checking permissions | 0.000132 | 0.000000 | 0.000000 |
| Sending data | 0.000042 | 0.000000 | 0.000000 |
| end | 0.000007 | 0.000000 | 0.000000 |
| query end | 0.000007 | 0.000000 | 0.000000 |
| closing tables | 0.000005 | 0.000000 | 0.000000 |
| removing tmp table | 0.000009 | 0.000000 | 0.000000 |
| closing tables | 0.000006 | 0.000000 | 0.000000 |
| freeing items | 0.000015 | 0.000000 | 0.000000 |
| logging slow query | 0.000005 | 0.000000 | 0.000000 |
| cleaning up | 0.000006 | 0.000000 | 0.000000 |
+----------------------+----------+----------+------------
- B-Tree 索引:大部分引擎都支持B-Tree索引
- HASH索引:只有memory引擎支持,使用场景简单。
- R-Tree索引:空间索引,Myisam引擎的一个特殊索引类型,主要用于地理空间数据类型
- Full-text:全文索引
mysql> show status like 'Handler_read%';
+-----------------------+-------+
| Variable_name | Value |
+-----------------------+-------+
| Handler_read_first | 1 |
| Handler_read_key | 6 |
| Handler_read_last | 0 |
| Handler_read_next | 16050 |
| Handler_read_prev | 0 |
| Handler_read_rnd | 0 |
| Handler_read_rnd_next | 297 |
+-----------------------+-------+
7 rows in set (0.00 sec)
- Handler_read_key :值高,证明索引正在工作;值低,说明增加索引得到的性能改善不高,因为索引不经常使用
- Handler_read_rnd_next:值高,意味着查询效率低,应该建立索引补救;
mysql> analyze table store;
+--------------+---------+----------+----------+
| Table | Op | Msg_type | Msg_text |
+--------------+---------+----------+----------+
| sakila.store | analyze | status | OK |
+--------------+---------+----------+----------+
1 row in set (0.00 sec)
mysql> check table store;
+--------------+-------+----------+----------+
| Table | Op | Msg_type | Msg_text |
+--------------+-------+----------+----------+
| sakila.store | check | status | OK |
+--------------+-------+----------+----------+
1 row in set (0.01 sec)
mysql> optimize table store;
+--------------+----------+----------+-------------------------------------------------------------------+
| Table | Op | Msg_type | Msg_text |
+--------------+----------+----------+-------------------------------------------------------------------+
| sakila.store | optimize | note | Table does not support optimize, doing recreate + analyze instead |
| sakila.store | optimize | status | OK |
+--------------+----------+----------+-------------------------------------------------------------------+
2 rows in set (0.04 sec)
mysql> alter table payment engine=innodb;
Query OK, 16049 rows affected (0.62 sec)
Records: 16049 Duplicates: 0 Warnings: 0
- alter table tbl_name disable keys;
- load data infile '/home/mysql/film_test3.txt' into table film_test4;
- alter table tbl_name enable keys;
- 因为innodb的表是按照主键的顺序保存的,索引将导入的数据按照主键的顺序排序,可以有效地提高导入数据的效率;
- 在导入数据前执行 set unique_checks=0 ,关闭唯一性校验,在导入结束后执行 set unique_checks=1,恢复唯一性校验;
- 如果应用使用自动提交的方式,建议在导入前执行:set autocommit=0,关闭自动提交,在导入完成之后,再开启;
- 使用多个值表的insert比单个insert语句快,因为多值表一起插入,缩减了客户端与数据库之间的连接,关闭等消耗;
- insert into test values(1,2),(2,3),(3,4).....
- 将索引文件和数据文件分在不同的磁盘上存放(利用建表中的选项)
- 当从一个文本装载一个表时,使用load data infile ,这通常比使用很多insert 语句快20倍;
- 如果从不同客户插入很多行,insert delayed 语句得到更高的速度;将数据都放入内存中,然后合并一起insert,减少客户端与数据库的交互
- 第一种通过有序索引顺序扫描直接返回有序数据,这种方式在使用explain 分析查询的时候显示为useing index,不需要额外的排序,操作效率较高。
- 第二种是通过返回数据进行排序,也就是filesort排序,所有不是通过索引直接返回排序结果的排序都叫filesort排序。
mysql> alter table customer add index idx_email_storeid (email,store_id);
Query OK, 0 rows affected (0.04 sec)
Records: 0 Duplicates: 0 Warnings: 0 mysql> explain select store_id,email, customer_id from customer order by email\G;
*************************** 1. row ***************************
id: 1
select_type: SIMPLE
table: customer
type: index
possible_keys: NULL
key: idx_email_storeid
key_len: 154
ref: NULL
rows: 652
Extra: Using index
1 row in set (0.00 sec)
mysql> alter table customer drop index idx_email_storeid;
Query OK, 0 rows affected (0.01 sec)
Records: 0 Duplicates: 0 Warnings: 0 mysql> alter table customer add index idx_storeid_email (store_id,email);
Query OK, 0 rows affected (0.03 sec)
Records: 0 Duplicates: 0 Warnings: 0 mysql> explain select store_id,email, customer_id from customer order by email\G;
*************************** 1. row ***************************
id: 1
select_type: SIMPLE
table: customer
type: index
possible_keys: NULL
key: idx_storeid_email
key_len: 154
ref: NULL
rows: 652
Extra: Using index; Using filesort
1 row in set (0.00 sec)
- select * from tabname order by key_part1,key_part2,......;
- select * from tabname where key_part1=1 order by key_part1 DESC, key_part2 DESC;
- select * from tabname order by key_part1 DESC, key_part2 DESC;
- select * from tabname order by key_part1 desc ,key_part2 asc;
- order by 的字段混合 ASC,DESC
- select * from tabname where key2 = 2 order by key1;
- 用于查询行的关键字与order by 中使用的不相同
- select * from tabname order by key1,key2;
- 两次扫描算法:首先根据条件取出排序字段和行指针信息,之后在排序区sort buffer中排序。优点是排序的时候内存开销较小,但排序效率低;
- 一次扫描算法:一次性去除满足条件的行的所有字段,然后在排序区sort buffer中排序后直接输出结果。优点排序效率比两次扫描高,但内存开销大;
mysql> explain select payment_date,sum(amount) from payment group by payment_date \G;
*************************** 1. row ***************************
id: 1
select_type: SIMPLE
table: payment
type: ALL
possible_keys: NULL
key: NULL
key_len: NULL
ref: NULL
rows: 16451
Extra: Using temporary; Using filesort
1 row in set (0.01 sec)
使用order by null优化group by
mysql> explain select payment_date,sum(amount) from payment group by payment_date ORDER BY NULL \G;
*************************** 1. row ***************************
id: 1
select_type: SIMPLE
table: payment
type: ALL
possible_keys: NULL
key: NULL
key_len: NULL
ref: NULL
rows: 16451
Extra: Using temporary
1 row in set (0.00 sec)
mysql> explain select film_id,description from film order by title limit 50,5;
+----+-------------+-------+------+---------------+------+---------+------+------+----------------+
| id | select_type | table | type | possible_keys | key | key_len | ref | rows | Extra |
+----+-------------+-------+------+---------------+------+---------+------+------+----------------+
| 1 | SIMPLE | film | ALL | NULL | NULL | NULL | NULL | 1134 | Using filesort |
+----+-------------+-------+------+---------------+------+---------+------+------+----------------+
1 row in set (0.00 sec)
mysql> explain select film_id,description from film inner join ( select film_id from film order by title limit 50,5) AS lim using(film_id);
+----+-------------+------------+--------+---------------+-----------+---------+-------------+------+-------------+
| id | select_type | table | type | possible_keys | key | key_len | ref | rows | Extra |
+----+-------------+------------+--------+---------------+-----------+---------+-------------+------+-------------+
| 1 | PRIMARY | <derived2> | ALL | NULL | NULL | NULL | NULL | 5 | |
| 1 | PRIMARY | film | eq_ref | PRIMARY | PRIMARY | 2 | lim.film_id | 1 | |
| 2 | DERIVED | film | index | NULL | idx_title | 767 | NULL | 55 | Using index |
+----+-------------+------------+--------+---------------+-----------+---------+-------------+------+-------------+
3 rows in set (0.00 sec)
mysql> select * from rental order by rental_id limit 5;
+-----------+---------------------+--------------+-------------+---------------------+----------+---------------------+
| rental_id | rental_date | inventory_id | customer_id | return_date | staff_id | last_update |
+-----------+---------------------+--------------+-------------+---------------------+----------+---------------------+
| 1 | 2005-05-24 22:53:30 | 367 | 130 | 2005-05-26 22:04:30 | 1 | 2006-02-15 21:30:53 |
| 2 | 2005-05-24 22:54:33 | 1525 | 459 | 2005-05-28 19:40:33 | 1 | 2006-02-15 21:30:53 |
| 3 | 2005-05-24 23:03:39 | 1711 | 408 | 2005-06-01 22:12:39 | 1 | 2006-02-15 21:30:53 |
| 4 | 2005-05-24 23:04:41 | 2452 | 333 | 2005-06-03 01:43:41 | 2 | 2006-02-15 21:30:53 |
| 5 | 2005-05-24 23:05:21 | 2079 | 222 | 2005-06-02 04:33:21 | 1 | 2006-02-15 21:30:53 |
+-----------+---------------------+--------------+-------------+---------------------+----------+---------------------+
mysql> select * from rental where rental_id > 5 order by rental_id limit 5;
+-----------+---------------------+--------------+-------------+---------------------+----------+---------------------+
| rental_id | rental_date | inventory_id | customer_id | return_date | staff_id | last_update |
+-----------+---------------------+--------------+-------------+---------------------+----------+---------------------+
| 6 | 2005-05-24 23:08:07 | 2792 | 549 | 2005-05-27 01:32:07 | 1 | 2006-02-15 21:30:53 |
| 7 | 2005-05-24 23:11:53 | 3995 | 269 | 2005-05-29 20:34:53 | 2 | 2006-02-15 21:30:53 |
| 8 | 2005-05-24 23:31:46 | 2346 | 239 | 2005-05-27 23:33:46 | 2 | 2006-02-15 21:30:53 |
| 9 | 2005-05-25 00:00:40 | 2580 | 126 | 2005-05-28 00:22:40 | 1 | 2006-02-15 21:30:53 |
| 10 | 2005-05-25 00:02:21 | 1824 | 399 | 2005-05-31 22:44:21 | 2 | 2006-02-15 21:30:53 |
+-----------+---------------------+--------------+-------------+---------------------+----------+---------------------+
5 rows in set (0.00 sec)
- mysql客户端和服务器间:半双工
- show processlist,实时查看SQL执行情况;
- 查询优化器:
- 统计信息:
- 每个表/索引的页面个数,
- 索引的基数,索引和数据行的长度,索引分布情况;
- 不考虑任何缓存假设数据读取需要一次IO;
- 优化策略:
- 静态优化,“编译时优化”
- 动态优化“运行时优化”
- 查询优化器的局限:
- 关联子查询,使用连接替代(5.6之后优化器已经自动优化了);
- union限制,需每个子句都limit 20控制临时表数量;
- 最大值和最小值优化,不能自动更据主键ID 选择;
- 不允许在同一表上更新和查询,可以使用内连接跳过限制;
- hint:
- use index
- ignore index
- force index
- 慢查询分析:
- show status like 'com%':
- 了解读写比例;
- 事务回滚比例;
- 视图连接mysql服务器的次数;
- 慢查询的次数;
- 定位低效SQL:慢查询日志
- explain分析低效SQL:
- explain extended 可以得到更清晰易读的SQL,多出来warning;
- explain partition 找到select到底是在哪个分区查询;
- show profile 分析SQL:
- show profile 能够在做SQL优化时帮助我们了解时间都耗费到哪里去了;
- 通过show profiles 找出query id,
- 通过show profile for query id 分析具体的SQL;能够看到执行过程中线程的每个状态和消耗的时间;也能根据cpu,io,等具体参数;
- trace:5.6之后可以使用,通过trace文件能够进一步了解为什么优化器选择A执行计划而不选择B执行计划,帮助我们更好地理解优化器的行为
- 索引使用情况:
- show status like 'Handler_read%'
- Handler_read_key:值高,证明索引正在工作;值低,说明增加索引得到的性能改善不高,因为索引不经常使用;
- Handler_read_rnd_next:值高,意味着查询效率低,应该建立索引补救;
- 定期分析表和检查表:使系统得到准确的统计信息,使优化器更好工作;
- 常用SQL优化:
- load:
- myisam,导入前,使索引失效,导入后,开启索引;
- innodb,关闭唯一性校验
- insert:多值表插入,
- order by:
- 索引排序:
- where条件和order by使用相同索引
- order by 的顺序和索引顺序相同
- order by 字段都是升序或降序,
- filesort:两次扫描算法,一次扫描算法;
- group by:group by 默认对字段排序,使用order by null 来禁止排序;
- 子查询可以使用连接代替
- or条件使用索引需要左右都要有索引段;
- 分页查询
- “延迟关联”,
- “首先获得第一组,然后使用书签方式”
- 将大查询分解为多个小查询
SQL业务审核与优化的更多相关文章
- SQL SERVER 查询性能优化——分析事务与锁(五)
SQL SERVER 查询性能优化——分析事务与锁(一) SQL SERVER 查询性能优化——分析事务与锁(二) SQL SERVER 查询性能优化——分析事务与锁(三) 上接SQL SERVER ...
- SQL点滴22—性能优化没有那么神秘
原文:SQL点滴22-性能优化没有那么神秘 经常听说SQL Server最难的部分是性能优化,不禁让人感到优化这个工作很神秘,这种事情只有高手才能做.很早的时候我在网上看到一位高手写的博客,介绍了SQ ...
- SQL Server 2014内存优化表的使用场景
SQL Server 2014内存优化表的使用场景 最近一个朋友找到走起君,咨询走起君内存优化表如何做高可用的问题 大家知道,内存优化表是从SQL Server 2014开始引入,可能大家对内存优化表 ...
- 使用阿里云RDS for SQL Server性能洞察优化数据库负载-初识性能洞察
简介 数据库性能调优通常需要较高数据库水平,并伴随较多的前期准备工作,比如收集各种性能基线.不同种类的性能指标.慢SQL日志等,这通常费时费力且效果一般,当面对多个数据库时总体拥有成本会大幅增加.今天 ...
- 【转】使用SQL Tuning Advisor STA优化SQL
SQL优化器(SQL Tuning Advisor STA)是Oracle10g中推出的帮助DBA优化工具,它的特点是简单.智能,DBA值需要调用函数就可以给出一个性能很差的语句的优化结果.下面介绍一 ...
- 【转】MySQL批量SQL插入各种性能优化
原文:http://mp.weixin.qq.com/s?__biz=MzA5MzY4NTQwMA==&mid=403182899&idx=1&sn=74edf28b0bd29 ...
- SQL Server数据库性能优化之SQL语句篇【转】
SQL Server数据库性能优化之SQL语句篇http://www.blogjava.net/allen-zhe/archive/2010/07/23/326927.html 近期项目需要, 做了一 ...
- SQL Server 查询性能优化 相关文章
来自: SQL Server 查询性能优化——堆表.碎片与索引(一) SQL Server 查询性能优化——堆表.碎片与索引(二) SQL Server 查询性能优化——覆盖索引(一) SQL Ser ...
- Sql Server查询性能优化之走出索引的误区
据了解绝大多数开发人员对于索引的理解都是一知半解,局限于大多数日常工作没有机会.也什么没有必要去关心.了解索引,实在哪天某个查询太慢了找到查询条件建个索引就ok,哪天又有个查询慢了,再建立个索引就是, ...
随机推荐
- iOS:ASIHttpRequest虽不更新,但仍值得详细了解
一.使用ASIHTTPRequest可以很方便的进行一下操作:同步/异步方式下载数据,定义下载队列,让队列中的任务按指定的并发数来下载(队列下载必须是异步的),提交表单,文件上传,处理cookie,设 ...
- 多种非接触卡 ATQA 字节说明
原文地址 13.56 MHz RFID Software An Open Source implementation of an NFC stack, and various related ut ...
- osglightpoint例子 [转]
该例子演示了光点的效果,主要应用osgSim库中的LightPoint.LightPointNode. SequenceGroup.BlinkSequence,osgSim库属于仿真库,扩展库.应用o ...
- 用C#实现木马程序
要实现木马服务的程序,主要实现以下几个功能:后台的运行(隐藏技术),控制码的接收与注册表的修改,下面对这三方面做介绍: 1.在VC#中,建立一个后台服务程序是很容易的,先建立一个新的C#的Window ...
- myeclipse发布项目到tomcat时项目名称与web应用名称不一致问题
工程名称原来为old,发布到tomcat webapps下后为old, 右键点击你的项目,然后选择重构---->重命名,项目名称改为new,但是发布名还是原来的名字.如果想让发布后的目录名为ne ...
- 【pyhon】Python里的字符串查找函数find和java,js里的indexOf相似,找到返回序号,找不到返回-1
# 例子: target='www.163.com' ')) ')==-1: print('263不存在于字符串'+target+'中') 运行: C:\Users\horn1\Desktop\pyt ...
- windows下基于apache的SVN启动失败修改
我用的svn版本是:Setup-Subversion-1.8.1-1.msi, Apache版本是httpd-2.2.25-win32-x86-no_ssl.msi,安装完后把SVN bin文件夹下的 ...
- it-tidalwave-semantic-aux-1.0.13.jar下载
今天来给大家分一下一下自己认为还是挺不错的jar包下载网址,it-tidalwave-semantic-aux-1.0.13.jar,作为java开发人员可能时时刻刻都在跟jar包打交道,即使这会用不 ...
- 【CODEFORCES】 A. Keyboard
A. Keyboard time limit per test 2 seconds memory limit per test 256 megabytes input standard input o ...
- oracle 存储过程 调用动态sql
oracle 存储过程 调用动态sql CreationTime--2018年8月16日11点25分 Author:Marydon 1.错误实现方式 --开始时间拼接' 00:00:00' V_S ...