<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0"
	xmlns:content="http://purl.org/rss/1.0/modules/content/"
	xmlns:wfw="http://wellformedweb.org/CommentAPI/"
	xmlns:dc="http://purl.org/dc/elements/1.1/"
	xmlns:atom="http://www.w3.org/2005/Atom"
	xmlns:sy="http://purl.org/rss/1.0/modules/syndication/"
	xmlns:slash="http://purl.org/rss/1.0/modules/slash/"
	>

<channel>
	<title>Some reminiscences, some memories &#187; 性能</title>
	<atom:link href="http://www.mikespook.com/index.php/tag/%e6%80%a7%e8%83%bd/feed" rel="self" type="application/rss+xml" />
	<link>http://www.mikespook.com</link>
	<description>Just another boring day</description>
	<lastBuildDate>Thu, 05 Aug 2010 14:36:19 +0000</lastBuildDate>
	<language>en</language>
	<sy:updatePeriod>hourly</sy:updatePeriod>
	<sy:updateFrequency>1</sy:updateFrequency>
	<generator>http://wordpress.org/?v=3.0.1</generator>
		<item>
		<title>Mysql 性能改进——最快实践</title>
		<link>http://www.mikespook.com/index.php/archives/361</link>
		<comments>http://www.mikespook.com/index.php/archives/361#comments</comments>
		<pubDate>Mon, 29 Jun 2009 05:10:01 +0000</pubDate>
		<dc:creator>mikespook</dc:creator>
				<category><![CDATA[Database]]></category>
		<category><![CDATA[mysql]]></category>
		<category><![CDATA[优化]]></category>
		<category><![CDATA[性能]]></category>

		<guid isPermaLink="false">http://www.mikespook.com/?p=361</guid>
		<description><![CDATA[没错，标题我没打错。这里不是最佳实践，而是最快实践。在服务器上线，巨大的压力导致相应缓慢的时候，最佳实践已经毫无意义。这个时候，目的只有一个：最快改善性能，给开发人员重新设计、调整应用留出一定的时间。 这里不是细腻的微调，而是最粗旷的拉升。用最简单（可快速实施），变更最少（尽量避免变更引入新的 bug 和问题）的方法迅速改善 mysql 的性能。所以我这里的最快实践，不一定是最好的，不一定是最有效的，但是一定是最快能看到性能改善的方法。 tmp_table_size 实施难度：容易 实施时间：短 实施效果：明显 tmp_table_size 默认 32M，根据手册上的说法，这个限制了内存临时表的大小。增大这个值可以立刻改善 mysql 的性能，虽然不是万灵丹，但却是个救命药。网上解释很多不多说了。 thread_cache_size 实施难度：容易 实施时间：短 实施效果：一般 在使用 SHOW STATUS; 查看 mysql 参数时，如果 thread_created 这个值很高的话，可以将 thread_cache_size 设置得大一些。内存允许的情况下，128 或者更大都是可以考虑的。mysql 通过内建的线程复用机制来实现了一个连接池。如果你的应用出现 max connection 的情况话（php 发生这种情况尤为严重），还是请开启 thread_cache_size 吧。 索引 实施难度：一般 实施时间：一般 实施效果：明显 不知什么时候，有一位高人说“对于 where 查询的条件字段，都加上索引会提高查询效率”。于是大家忙不停的将所有可能的字段都加上了索引。潘多拉的魔盒从此打开…… 上图： 这样的表中，假设 t2 的总记录数不超过10 条。如果 t2_c1 这个字段有这样的查询 select * from t1 [...]]]></description>
			<content:encoded><![CDATA[<p>没错，标题我没打错。这里不是最佳实践，而是最快实践。在服务器上线，巨大的压力导致相应缓慢的时候，最佳实践已经毫无意义。这个时候，目的只有一个：最快改善性能，给开发人员重新设计、调整应用留出一定的时间。</p>
<p>这里不是细腻的微调，而是最粗旷的拉升。用最简单（可快速实施），变更最少（尽量避免变更引入新的 bug 和问题）的方法迅速改善 mysql 的性能。所以我这里的最快实践，不一定是最好的，不一定是最有效的，但是一定是最快能看到性能改善的方法。<span id="more-361"></span></p>
<h1>tmp_table_size</h1>
<p>实施难度：容易</p>
<p>实施时间：短</p>
<p>实施效果：明显</p>
<p>tmp_table_size 默认 32M，根据手册上的说法，这个限制了内存临时表的大小。增大这个值可以立刻改善 mysql 的性能，虽然不是万灵丹，但却是个救命药。网上解释很多不多说了。</p>
<h1>thread_cache_size</h1>
<p>实施难度：容易</p>
<p>实施时间：短</p>
<p>实施效果：一般</p>
<p>在使用 SHOW STATUS; 查看 mysql 参数时，如果 thread_created 这个值很高的话，可以将 thread_cache_size 设置得大一些。内存允许的情况下，128 或者更大都是可以考虑的。mysql 通过内建的线程复用机制来实现了一个连接池。如果你的应用出现 max connection 的情况话（php 发生这种情况尤为严重），还是请开启 thread_cache_size 吧。</p>
<h1>索引</h1>
<p>实施难度：一般</p>
<p>实施时间：一般</p>
<p>实施效果：明显</p>
<p>不知什么时候，有一位高人说“对于 where 查询的条件字段，都加上索引会提高查询效率”。于是大家忙不停的将所有可能的字段都加上了索引。潘多拉的魔盒从此打开……</p>
<p>上图：</p>
<p><a href="http://www.mikespook.com/wp-content/uploads/2009/06/nouse_index.JPG"><img class="size-full wp-image-362 alignnone" title="nouse_index" src="http://www.mikespook.com/wp-content/uploads/2009/06/nouse_index.JPG" alt="nouse_index" width="554" height="114" /></a></p>
<p>这样的表中，假设 t2 的总记录数不超过10 条。如果 t2_c1 这个字段有这样的查询 select * from t1 where t2_c1 = 1; 不少童鞋都会在 t2_c1 上加多一个索引，为了让这个搜索更快一些。这会是真的么？</p>
<p>显然不是！</p>
<p>在 t2_c1 字段的数据差异很小的情况下，使用索引不会比全表扫描快。更有可能的情况是，索引不但导致 t1 表数据修改变慢，同时导致查询变慢。为什么？大家先学习一下“随机存取”和“连续预读”的差异就明白了。不必要的索引还是去掉吧！我甚至见过索引比数据都大的表，如果读索引的速度比直接读数据都慢，这会有什么后果？太可怕了……</p>
<h1>只查要用到的列</h1>
<p>实施难度：大</p>
<p>实施时间：长</p>
<p>实施效果：明显</p>
<p>这绝对是老生常谈，但是总有人不在意。他们心中有疑问：“为什么？为什么？为什么 SELECT * FROM table 会慢？”他们心中有梦想：“这不可能吧，扫描的都是那么多数据，那几个表。索引使用也一样有效。”</p>
<p>的确，数据扫描的记录数不会因为列的限制而减少，索引的影响也不因为列的限制而改变。不过每个内存页面中存放记录的条数会因为列的不同发不同。为了说明这个问题，我专门构造了一个 140万条记录，每条记录大约 50字节的表。如果应用只是用结果集的主键，使用 select * from table 查询比使用 select id from table 慢了近一倍。其实道理也很简单，结果集行记录变小了，内存页面中每个页面可以放的记录数就多了。内存页面的交换就减少，I/O减少。同时采用连续预读I/O效率提高。进而查询速度提升。</p>
<p>在业务逻辑都确定的情况下，每个方法所用到的字段也都确定了。这个时候可以快速将那些没有用到的字段从查询语句中剔除。查询效率自然提升。</p>
<p>按照上面的顺序进行快速优化，可以在不改变业务逻辑和代码逻辑的情况下迅速提升 mysql 性能，同时可避免应用长时间下下线，也为进一步优化争取时间。何乐而不为？</p>
<p>如果还有更快、更好的方法，我再补充吧！</p>
<p><strong>“性能是改进出来的，不是设计出来的！”</strong></p>
]]></content:encoded>
			<wfw:commentRss>http://www.mikespook.com/index.php/archives/361/feed</wfw:commentRss>
		<slash:comments>1</slash:comments>
		</item>
		<item>
		<title>关于 web game 运算负载的只言片语</title>
		<link>http://www.mikespook.com/index.php/archives/274</link>
		<comments>http://www.mikespook.com/index.php/archives/274#comments</comments>
		<pubDate>Thu, 08 Jan 2009 14:50:31 +0000</pubDate>
		<dc:creator>mikespook</dc:creator>
				<category><![CDATA[Game]]></category>
		<category><![CDATA[webgame]]></category>
		<category><![CDATA[性能]]></category>

		<guid isPermaLink="false">http://www.mikespook.com/index.php/archives/274</guid>
		<description><![CDATA[没办法整理成长篇大论了，就写点只言片语吧。 起因看这里：http://www.javaeye.com/topic/305801?page=1 －－－－－－－－－－－－－－－－－ 看了一遍，忍不住了，插句嘴～～ webgame 根本没有，也不需要什么大量实时数据要处理～～ 例如类似部落战争的行军，这个其实早就根据所选兵种、指挥官、宝物等等生成了一个事件存放在事件队列中（可能是内存对象、可能是某种数据缓存更有可能是数据库的某条记录），然后服务器在那个事件事件到达的时候取出事件对象执行一下，得到一个结果，接着存起来。至于行军途中到哪个位置如何如何，那是给玩家想象的，服务器根本不管。总之，事件运算有三种方式：1。玩家请求时已经运算完成，到了特定时间通知玩家。2。事件执行时间运算完成，并通知玩家。3。在服务器空闲时，处理待处理的运算，到了特定时间通知玩家。 webgame， MMO 实时性不是首先考虑的。例如资源增长，如果服务器有 10W 激活用户，在同一时间增长资源是几乎不可能的。那就将一分钟划分60秒（废话），每秒开一个新线程来处理一部分用户（10W/60）的资源增长。资源增长基本上就是浮点数加减乘除，对于现在的 cpu 来说，并不是很高。何况服务器 N 个 cpu…… 简单的说，webgame 不像 MMO 需要“随时”客户端跟服务器端通讯。更多情况，web 服务器通过某种方式从 game server 中获得一个当前游戏状态的快照返回到浏览器。并从浏览器接收数据，然后在一个可接受的，合理的时间内去修改 game server 的状态。请再次注意，again！这不是“实时”的！ 最后再罗嗦一下，webgame 的 game server 更多情况下是一个 task server。它不需要去预测客户端行为，也不需要计算碰撞、寻找可行路径…… 另外，我个人的体会，RPG 类型的 webgame 在运算负载上来说，远小于策略形的。并且通常只需要 3 台服务器配合：web server、task server、db server。 哦，还有，如果用 flash 的 socket 方式开发，不在上述范围内。当这种模式是个客户端能力稍差的 MMO 好了。]]></description>
			<content:encoded><![CDATA[<p>没办法整理成长篇大论了，就写点只言片语吧。<br />
起因看这里：<a href="http://www.javaeye.com/topic/305801?page=1" target="_blank">http://www.javaeye.com/topic/305801?page=1<br />
</a> －－－－－－－－－－－－－－－－－<br />
看了一遍，忍不住了，插句嘴～～</p>
<p>webgame 根本没有，也不需要什么大量实时数据要处理～～</p>
<p>例如类似部落战争的行军，这个其实早就根据所选兵种、指挥官、宝物等等生成了一个事件存放在事件队列中（可能是内存对象、可能是某种数据缓存更有可能是数据库的某条记录），然后服务器在那个事件事件到达的时候取出事件对象执行一下，得到一个结果，接着存起来。至于行军途中到哪个位置如何如何，那是给玩家想象的，服务器根本不管。总之，事件运算有三种方式：1。玩家请求时已经运算完成，到了特定时间通知玩家。2。事件执行时间运算完成，并通知玩家。3。在服务器空闲时，处理待处理的运算，到了特定时间通知玩家。</p>
<p>webgame， MMO 实时性不是首先考虑的。例如资源增长，如果服务器有 10W 激活用户，在同一时间增长资源是几乎不可能的。那就将一分钟划分60秒（废话），每秒开一个新线程来处理一部分用户（10W/60）的资源增长。资源增长基本上就是浮点数加减乘除，对于现在的 cpu 来说，并不是很高。何况服务器 N 个 cpu……</p>
<p>简单的说，webgame 不像 MMO 需要“随时”客户端跟服务器端通讯。更多情况，web 服务器通过某种方式从 game server 中获得一个当前游戏状态的快照返回到浏览器。并从浏览器接收数据，然后在一个可接受的，合理的时间内去修改 game server 的状态。请再次注意，again！这不是“实时”的！</p>
<p>最后再罗嗦一下，webgame 的 game server 更多情况下是一个 task server。它不需要去预测客户端行为，也不需要计算碰撞、寻找可行路径……<br />
另外，我个人的体会，RPG 类型的 webgame 在运算负载上来说，远小于策略形的。并且通常只需要 3 台服务器配合：web server、task server、db server。</p>
<p>哦，还有，如果用 flash 的 socket 方式开发，不在上述范围内。当这种模式是个客户端能力稍差的 MMO 好了。</p>
]]></content:encoded>
			<wfw:commentRss>http://www.mikespook.com/index.php/archives/274/feed</wfw:commentRss>
		<slash:comments>3</slash:comments>
		</item>
	</channel>
</rss>
