MySQL最佳优化完美攻略

所需积分/C币:23 2017-07-07 16:08:04 537KB PDF

强烈推荐 MySQL最佳优化完美攻略
优化操作系统 不要交換区。如果内存不足,增加更多的内存或配置你的系统使用较少内存。 不要使用NFS磁盘(会有NFS锁定的问题)。 增加系统和 MySQL服务器的打开文件数量。(在 safe_ mysqld脚本中加入 ulimit-n#)。 增加系统的进程和线程数量。 如果你有相对较少的大表,告诉文件系统不要将文件打碎在不同的磁道上( Solaris)。 使用支持人文件的文件系统( Solaris)。 选择使用哪和文件系统。在 Linux上的 Reiserfs村于打开、读写都非常快。文件裣耷只需几秒种 选择应用编程接口 PERL: 可在不同的操作系统和数据库之同移植。 适官快速原型。 应该使用 DBI/DBD接口。 比PERL易学 使用比PERL少的资源。 通过升级到PHP4可以获得更快的速度 MySQL的原生接口。 较快并赋予更多的控制。 低层,所以必须付出更多 C++ 较高层次,给你更多的时间来编写应用 仍在开发中 ODBC: 运行在 Windows和Un上。 几乎可在不同的SQL服务器间移植。 较慢。 MyODBC只是单的直通驱动程序,比用原生接口慢19%。 有很多方法做同样的事。很难像很多ODBC驱动程序那样运行,在不同的领域还有不同的错误。 问题成堆。 Microsoft偶尔还会改变接凵。 不明朗的未来。( Microsoft更推崇OLE而非ODBC) JDBC: 理论上叫在不同的操作系统何时据库阳移植。 可以运行在web客户端 Python和其他 可能不错,可我们不用它们。 优化应用 应该集中精力解决问题 kider 在编写应用时,应该决定什么是最重要的: 速度 操作系统间的可栘植性 sQL服务器间的可移植性 使用持续的连接。 缓存应用中的数据以减少SQL服务器的负载。 不要查询应用中不需要的列 不要使用 SELECT* FROM tab| e name. 测试应用的所冇部分,但将大部分精力放在在可能最坏的合理的负载下的测试整体应用。通过以一种 模块伈的方式诖行,你应该能用一个快速哑模块″替代找到的瓶颈,然后很容易地标出下一个瓶颈。 如果在一个批处理中进行大量修改,使用 LOCK TABLES。例如将多个 UPDATES或 DELETES集中 在一起 应该使用可移植的应用 Perl DBI/DBD ODBC JDBC Python(或其他有普遍SQL接口的语言) 你应该只使用存在于所有目的SqL服务器中或可以很容易地用其他构造模拟的SQL构造 www.mysql.com上的Crash-me页可以帮助你 为操作系统/SQL服务器编写包装程序来提供缺少的功能。 如果你需要更快的速度 应该找出瓶颈(C門∪、磁盘、内存、SQL服务器、操作系统、API或应用)并集中全力解诀。 使用给予你更快这度/灵活性的扩展。 逢渐了解SqL服务器以便能为你的问题使用叫能最快的SQL构造并遆免瓶颈。 优化表布局和查询。 使用复制以获得更忺的选择( select)速度 如果你有一个慢这的络连接数据库,使用压缩客户/服务器协议 不要害怕时应用的第一个版本不能完美地移植,在你解决问题时,你总是可以在以后优化它。 优化 挑选编译器和编译选项。 为你的系统寻找最好的启动选项。 通读 MySQL参考手册并阅读 Paul du bios的《 MySQL》一书。(已有中文版-译注) 多用 EXPLAIN SELECT、 SHOW VARIABLES、 SHOW STATUS和 SHOW PROCESSLIST 了解查询优化器的工作原理。 优化表的格式。 维护你的表( myisamchk、 CHECK TABLE、 OPTIMIZE TABLE 使用 MySQL的扩展刀能以让一切快速完成 kider 如果你注意到了你将在很多场合需要某些函数,编写 MYSQL UDF函数 不要使用表级或列级的 GRANT,除非你确实需要。 购买 MySQL技术支持以帮助你解决问题:) 编译和安装 通过位你的系统挑选可能最妤的编译器,你通常可以获得10-30%的性能提高。 在 Linux/Inte平台上,用pgcc(gcc的奔腾芯片优化版)编译 MySQL。然而,二进制代码将只能运 行在Inte奔腾CPU上 对于一种特定的平台,使用 MySQL参考手册上推荐的优化选项。 般地,对特定CPU的原生编译器(如 Sparc的 Sun Workshop)应该比gcc提供更好的性能,但不 总是这样。 用你将使用的字符集编译 MySQL 静态编译生成 mysqld的执行文件(用-wth- mysqld-ldflags= all-static)并用 strip sql/ mysqld整 理最终的执行文件 注意,既然MySαL不使用C++扩展,不带扩展支持编译№ySQL将嬴得巨大的性能提高。 如果操作系统支持原生线程,使用原生线程(而不用mit- pthreads)。 用 MySQL基准测试来测试最终的二进制代码。 维护 如果可能,偶尔运行一下 OPTIMIZE table,这对大量更新的变长行非常重要。 偶尔用 myisamchk-a更新一下表中的键码分布统计。记住在做之前关掉 MYSQL 如果冇碎片文仵,可能值得将所冇文件复制到疔一个磁盘上,清除原来的磁盘并拷回文件。 如果遇到问题,用 myisamchk或 CHECK table检查表。 用 mysqladmin-10 precesslist extended- status监控 MySQL的状态。 用 MySQL GUI客户程序,你可以在不同的窗口内监控进程列表和状态。 使用 mysqladmin debug获得有关锁定和性能的信息。 优化 扬SQL之长,其它事情交由应去做。使用SQL服务器来做: 找出基于 WHERE子句的行。 JOIN表 GROUP BY ORDER BY DISTINCT 不要使用SQL来做: 检验数据(如日期) 成为一只计算器 技巧 明智地使用键码 键码适合搜索,但不适合索引列的插入/更新 kider 保持数捃为数据库第三范式,但不要担心冗余信息或这如果你需要更快的度,创建总结表。 在大表上不做 GROUP BY,相反创建大表的总结表并查询它。 UPDATE table set count= count+1 where key_ column= constant非常快 对于大表,或许最好偶尔生成总结表而不是一直保持总结表。 允分利用 INSERT的默认值。 不同服务器的速度差别(以秒计) 十---------------------+------- 通过键码读取2000000行:|NT Li 十 十 Mysql 367 249 -------+ I mysql_odbc 464 db2 odbc 1206 ------------------------+--------+---------+ informix_odbc 121126 十 I ms-sql odbc 1634 十-----------------+--------+ oracle odbc 20800 solid odbc 877 --------------+--------+---------+ sybase_odbc 17614 + 插入350768行 NT nuX 十 mysql 381 206 十-----------------------+--------+--------+ I mysql_odbc 619 Idb2_odbc 3460 ------+ informix_odbc 2692 Ims-sql_odbc 4012 oracle odbc 11291| I solid_odbc 1801 kide -----------------------+--------+---------+ I sybase_odbc 4802 -----------------------+-------- 十 在上述测试中, MySQL配置8M高速缓存运行,其他数据库以默认安装运行。 重要的 启动选项 back log如果需要人量新连接,侈改它 thread cache_size如果需要大量新连接,修改它。 key buffer_size素引页池,可以设成很大。 bab cache_ size BDB表使用的记录和键吗高速缓存。 table cache如果有很多的表和并发连接,修改它 delay key write如果需要缓存所有键码写入,设置它 log_slow_ queries找出需化大量时间的查询。 max heap table size用于 GROUP BY sort buffer用于 ORDER BY和 GROUP BY myisam_sort_ buffer size用于 REPAIR TABLE join buffer size在进行无键吗的联结时便用。 优化表 MYSQL拥有一套丰富的类型。你应该对每一列尝试使用最有效的类型。 ANALYSE过程可以帮助你找到表的最优类型: SELECT* FROM table name procedure ANALYSEO 对于不保存NULL值的列使用 NOT NULL,这对你想索引的列尤其重要。 将ISAM类型的表改为 MYISAM。 如果可能,用固定的表格式创建表 不要索引你不想用的东。 利用 MySQL能按一个索引的前缀进行查询的事实。如果你有索引 INDEX(ab),你不需要在a上的 索引。 不在长 CHAR/VARCHAR列上创建索引,而只索引列的一个前缀以节省存储空间。 CREATE TABLE table_name(hostname Char(255 not null, index(hostname(10) 对每个表使用最有效的表格式。 在不同表中保存相同信息的列应该有同样的定义并具有相同的列名。 如何次存储数据 数拆库以目录存储。 表以文什存储。 列以变长或定长格式存储在文件中。对BDB表,数据以页面形式存储 支持基于内存的表 数捱库和表可在不同的嵫盐上用符号连接起来。 在 Windows上, MySQL支持用,sym文件内部符号连接数据库。 kider MY SQL表类型 HEAP表:固定行长的表,只存储在内存中并用HASH索引进行索引 ISAM表: MYSQL3.22中的早期 B-tree表格式。 My IASM:IASM表的新版本,有如下扩展: 进制层次的可移植性。 NULL列索引。 对变长行比ISAM表有更少的碎片。 支持大文件。 更好的索引压缩。 受好的键吗统计分布。 更好和更快的auto_ increment处理。 来自 Sleepycat的 Berkeley DB(BDB)表:事务安仝(有 BEGIN WORK/ COMMIT| ROLLBACK 行类型(专指 表 如果所有列是定长格式(没有 VARCHAR、BLOB或TEXT), MySQL将以定长表格式创建表,否则表 以动态长度格式创建。 定长格式比动态长度格式快很多并更安全。 动态长度行格式一般占用较少的存储空间,但如果表频繁更新,会产生碎片 在某些情况下,不值得将所有 ARCHAR、BLOB和TEX列转移到另一个表中,只是获得主表上的 更快速度 利用 myiasmchk(对ISAM,pack_iasm),可以创建只读压缩表,这使盐使用率最小,但使用 慢遼磁盘时,这非常不错。压缩表充分地利用将不再更新的日志表 缓存 1、 MySQL高速缓存(所有线程共享,一次性分配) 键码缓存: key_ buffer_size,默认BM。 表缓存: table cache,默认64。 线稈缓存: thread cache size,默认0。 主机名缓存:可在编译时修改,默认128。 内存映射表:目前仅用于压缩表。 注意: MYSQL没有运行高速缓存,而让操作系统处理。 2、 MySQL缓存区变量(非共享,按需分配) sort buffer: ORDER BY/ GROUP BY record buffer:扫描表 join_ buffer_size:元键联结 myisam sort buffer size: REPAIR TABLE net_ buffer_length:对于读SQL语句并缓存结果。 tmp table size:临时结果的HEAP表大小 kide 表高速缓存工作原理 每个 MyISAM表的打开灾例( instance)使用一个索引文件和一个数据文件。如果表被两个线程使用或 在同一条查询中使用两次, MYIASM将共享索引文件而是打开数据文件的另一个实例。 如果所有在高速缓存中的表都在使用,缓存将临时増加到比表缓存尺寸大些。如果是这样,下一个被 释放的表将被关闭。 你可以通过检査 mysqld的 Opened_tables变量以检査表缓存是否太小。如果该值太高,你应该增 大表高速缓存。 扩展优化提供更快的速度 使用优化的表类型(HEAP、 MYIASM或BDB表)。 对数据使用优化的列。 如果可能使用定长行 使用不同的锁定类型( SELECT HIGH_ PRIORITY, INSERT LOW PRIORITY) auto increment REPLACE(REPLACE INTO table_name VALUES (.D) INSERT DELAYED LOAD DATA INFILE/ LOAD FILEO 使用多行 INSERT一次插入多行。 SELECT INTO OUTFILE LEFT JOIN, STRAIGHT JOIN LEFT]OIN,结合 IS NULL ORDER BY可在某些情况下使用键码 如果只查询在一个索引屮的列,将只使用索引树解决查询。 联结一般比子查询快(对大多数SQL服务器亦如此) LIMIT seleCt from table1 where a 10 LIMiT 10.20 DeLEtE from table 1 where a 10 LIMIT 10 foo in(常数列表)高度优化 GET_LOCK(/RELEASE_LOCKO LOCK TABLES INSERT和 SELECT可同时运行 UDF函数可装载进一个正在运行的服务器 压缩只读表。 CREATE TEMPORARY TABLE CREATE TABLE SELECT 带RAID选项的 MyIASM表将文件分割成很多文件以突破某些文件系经的2G限制。 Delay keys 复制功能 kider 何时使用索引 对一个键码使用>,>=,=,<,<=, IF NULL和 BETWEEN SELECT FROM table name Where key_ part1=l and key_part2>5; SELECT FROM table_ name Where key_part1 IS NULL 当使用不以通配符开始的LIKE SELECT FROM table_name Where key_partl LIKE jani% 在进行联结时从另一个表中提取行时 SELECT from tl, t2 where t1.col=t2. key_part 找出指定索引的MAX()或MIN(值 SELECT MIN(key_part2), MAX(key_part2) FROM table_name where key_part1=10 个键码的前缀使用 ORDER BY或 GROUP BY SELECT FROM foo ORDER BY key_parti, key_part2, key_part3 在所有用在查询中的列是键码的一部分时间 seleCt key part 3 From table name Where key part1=1 何时不使用索引 如果 MySQL能估计出它将可能比扫描整张表还要快时,则不使用索引。例如如果 key part1均匀分 布在1和100之间,下列査询屮使用索引就不是很好: SELECT FROM table name where key part 1 1 and key part1 <90 如果使用HEAP表且不用=搜索所键码部分。 在HEAP表上使用 ORDER BY。 如果不是用键码第一部分 SELECT FROM table_name Where key_part2=1 如果使用以一个通配符开始的LIKE SELECT* FROM table_ name WheRe key_part1 LIKE jani%o 索一个索引而在另一个索引上做 ORDER BY SELECT from table name WHERE key part1 = ORDER BY key2 学会使用 对于每一条你认为太慢的查询使用 EXPLAIN! kider

...展开详情

评论 下载该资源后可以进行评论 1

蓝色天银 还可以吧,分要得有点多
2018-07-11
回复
img

关注 私信 TA的资源

上传资源赚积分,得勋章
    最新推荐