关于MySQL查询约束条件类型需要注意的一点

最近在工作中遇到了数据库服务器产生很多读写队列的问题,于是要求大家开始优化我们的SQL语句。

下面是查询quotedata_history表中的code字段的SQL语句,其中code字段的类型是varchar(6)。

20121217210533

以上查询语句是:

SELECT * FROM quotedata_history WHERE `code` = 600000

大家可以看到这个语句的code条件600000是没有加引号的,通过Navicate的截图大家可以看到这次查询花了14.169秒。

20121217210534

以上查询语句是:

SELECT * FROM quotedata_history WHERE `code` = '600000'

大家可以看到这个语句的code条件600000加了引号,通过Navicate的截图大家可以看到这次查询花了0.087秒。

这两个查询的效率相差实在是太大了!

所以大家要注意,以后查询数据库的时候,如果字段是string类型的,条件的值必须加上单引号,以提升查询的效率!

MySQL数据库浮点数精度误差的解决方法(建议尽量使用定点数)

    今天在工作中发现MySQL数据库的一个数据表中有一个叫做fund1的字段, 在Navicat中看到有一条记录fund1的值为0.04,我在PHP程序中使用where查询fund1等于0.04的时候根本没有结果,用Navicat的筛选查询也没有出现任何结果。
    于是我想起了之前见到很多浮点数例如0.04存放在数据库中的时候,实际上的值是0.03989balabala这样的一大串随机数,只是设置了这个字段的长度和精确到小数点后几位之后就通过四舍五入显示为0.04,实际上这个值不等于0.04。用PHP查询得到的数据也是诸如0.03989balabala这样的一大串随机数,所以之前我都是用PHP的round()函数来四舍五入,虽然可以解决问题,但是像查询fund1=0.04这样的条件就没办法使用数据库直接实现,而是要通过程序来处理结果。
    后来,我把数据库中fund1字段的类型改成了定点数(decimal),长度和精确到小数点后几位都不变,这样之后就能够准确实现查询了。我在网上还找到了几条建议:
    在今后关于浮点数和定点数的应用中,大家要记住以下几点:
    1、浮点数存在误差问题;
    2、对货币等对精度敏感的数据,应该用定点数表示或存储;
    3、编程中,如果用到浮点数,要特别注意误差问题,并尽量避免做浮点数比较;
    4、要注意浮点数中一些特殊值的处理。

解决Incorrect integer value: ” for column ‘hits’ at row 1

虽然这个问题是我在开发项目的时候碰到的,是在我看他人分享文章中看到的,但是我觉得十分有必要记录一下。

假如在数据插入数据库时写查询语句“insert into log  values(”,’admin’,’31’,’002t’)”,从语法上说是没有错误的。但是在执行的时候有可能正确,有可能报错。这是为什么呢?这取决于你的mysql版本以及你的配置文件的配置。

mysql5以上的版本如果是空值要写NULL。

解决办法是更改mysql中的配置 my.ini      my.ini中查找sql-mode,默认为sql-mode=”STRICT_TRANS_TABLES,NO_AUTO_CREATE_USER,NO_ENGINE_SUBSTITUTION”,将其修改为sql-mode=”NO_AUTO_CREATE_USER,NO_ENGINE_SUBSTITUTION”,重启mysql后即可。那么如果是虚拟主机或者是空间怎么办了。如果你能让空间商帮你改那是最好。

但是我的最终建议,还是写规范点,空值就写null,这样就不会出问题啦。

在MySQL数据库中建立唯一索引

MySQL中建立唯一索引的SQL语句:

ALTER TABLE `original` ADD UNIQUE (`code`) ;

当MySQL中没有建立唯一索引时候,UPDATE时就会锁住整个表,当建立了索引,就会锁住相对应的记录。所以在查询,或更新操作比较频繁时候,都建议建立唯一索引,MySQL唯一索引是效率最高的索引。

Tonitech版权所有 | 转载请注明出处: http://www.tonitech.com/?p=926

深入了解Memcache(原理、机制详细介绍)

        Web应用程序都需要与数据打交道,它要能够处理数据:既要存储一个用户提交的数据,又要检索要显示的数据,这是一个Web应用程序的主要功能。数据是关系到可伸缩性方面最重要的议题,它决定了应用程序能够达到多快的速度和多高的效率。我们知道MySQL是一个关系型的数据库系统,组织数据并存储在MySQL中,而且它也是Web应用程序最主要的数据源。数据库是持久的数据存储,其中存储着我们所有的数据,而且Web应用程序也可以使用数据库中的数据,但是,要从一个数据库中检索数据确实需要付出一些代价,这取决于所执行的数据库查询的类型及其后续检索的结果集。

        为了让应用程序能够正常运行,我们经常需要从数据库中检索各种类型的数据,包括频繁变化的数据,如用户或者会话数据;以及不经常变化的数据,如实际的页面内容。为了得到这些数据必须访问数据库,这样将严重影响性能,从而也成为需要考虑的主要问题所在。这就是不要总是去访问数据库来获取所需的数据,而是使用缓存的原因。这正是memcached要解决的问题。

        memcached是一个高性能、分布式的内存对象缓存系统,它实际上就是一个简单的内存服务器,能够为应用程序存储数据提供一个缓存层,从而减轻数据库的负担。存储在memcached中的数据并不持久,这意味着当memcached的服务器关机或者重新启动时,它的内容就消失了,而且它没有故障转移或者认证,因此完全由应用程序使用memcached来实现数据的管理和不断更新。

        memcached有一个称为最近最少使用(Least Recently Used LRU)的缓存的结构,从而当memcached的存储空间满时,最早存储和刚被访问过的数据将会被更新的内容替换。另外,memcached对于存储的数据还提供到期的超时设定,从而可以把数据存储设置为到将来某个时间到期,也可以什么也不设置。当memcached达到它的存储容量时,将会先替换到期的数据,然后替换刚被使用过的数据。

        memcached可以运行在任何配置类型中:一台或者多台服务器上,或者甚至在同一台服务器上运行多个实例。memcached的服务器只提供一个存储结构,在这个存储结构中,数据按照键值存储,而检索功能则通过使用一个散列查找表来实现。从真正意义上把它们全部粘连在一起的工作是在memcached的客户端实现的,在那里把一个散列的键值引用到正在被存储或者检索的数据上。它使用一种特殊的散列算法来决定某一个或者多个键的请求应该被发送到哪几台服务器中。一旦客户端知道某一特定条目请求的是哪台服务器,它就会以并行的方式把请求发送到相应的服务器上。然后每台服务器使用它自己的散列键查找表来检索存储条目,随后把结果发送回客户端。接着客户端把这些结果聚集在一起以供应用程序使用。

        由于memcached使用内存而不是磁盘来存储数据,因而它存储与检索数据的速度是特别快捷的(本站的http://www.tonitech.com/?p=263一文有详细讲解这一原理)。它对CPU的要求也不太高,在同一台运行Apache Web服务的服务器上也可以运行memcached,或者在有空闲内存可用的任何服务器上也能运行memcached。

        对于memcached,一种普通的体系架构设置是拥有许多简单配置的服务器,而每台服务器的唯一目的就是提供内存。因为,相对于数据库对CPU能力的需求更大而言,memcached却是对于内存容量需求更大,所以,在针对服务器的硬件投入方面,更容易满足memcached的要求。这样,就可以使用多台较低端的服务器来为应用程序提供一个分布式内存缓存层,从而在可伸缩性方面更容易实现,费用也不太昂贵。

        在memcached出现之前,开发人员想避免通过访问数据库来获取数据,曾经使用过各种模式来缓存数据。其中有一种方法是在Web进程中缓存数据(因为mod-perl是持久的)。这种方法的一个致命问题是,每个子进程最后都拥有一份其他进程己经缓存的数据副本,从而导致重复数据填充在各个线程及其子线程中。无论如何,最佳的缓存方法当然是使用内存,而不是磁盘。

        随着技术的发展,出现了memcached,当初,Brad Fitzpatrick开发的memcached只是用于Livej ournal.com网站,他想要有一个比那些当时已经存在的方案更好的缓存解决方案。Livejournal是一个社交网站,这个网站每天有成千上万的用户和动态页面流量。原先成千上万的页面流量的所有这些数据都是通过访问数据库来实现的,而通过使用memcached现在只需要一个轻量级的缓存就可以获取数据了,从而减轻了数据库的负担,可以说数据库几乎没有任何负担。