1.规划
2.需求分析
3.概念模型设计
4.逻辑设计
5.物理设计
6.程序编制及调试
7.运行及维护。php
CREATE DATEBASE database_namejava
SHOW DATABASEmysql
USE database_namec++
DORP DATABASE database_nameweb
SHOW ENGINES;redis
SHOW VARIABLES LIKE ‘storage_engine%’sql
CRATE TABLE table_name(
Field_name data_type,
Field_name data_type,
…
Field_name data_type
)shell
DESC[RIBE] table_name数据库
DROP TABLE table_name编程
ALTER TABLE old_table_name RENAME [TO] new_table_name
ALTER TABLE table_name ADD field_name data_type
SHOW CREATE TABLE table_name
ALTER TABLE table_name ADD field_name data_type FIRST
ALTER TABLE table_name ADD field_name data_type AFTER field_name
ALTER TABLE table_name DORP field_name
ALTER TABLE table_name MODIFY field_name data_type
ALTER TABLE table_name CHANGE old_field_name new_field_name old_data_type
ALTER TABLE table_name CHANGE old_field_name new_field_name new_data_type
ALTER TABLE table_name MODIFY field_name_1 data_type [FIRST]|[AFTER field_name_2]
Field_name data_type NOT NULL
Field_name data_type DEFAULT default_value
一、Field_name data_type UNIQUE
二、CONSTRAINT constraint_name UNIQUE(field_name)
Field_name data_type PRIMARY KEY
CONSTRAINT constraint_name PRIMARY KEY (field_name_1, field_name_2, …)
Field_name data_type AUTO_INCREMENT
CONSTRAINT constraint_name FOREIGN KEY(filed_name)
REFERENCES other_table_name(other_field_name)
[表示可先项]
|表示选择
table_name(
column_name
INDEX|KEY [index_name](field_name [(index_length)] [ASC|DESC])
)
一、CREATE INDEX index_name ON table_name (
field_name [(index_length)] [ASC|DESC])
二、ALTER TABLE table_name ADD INDEX|KEY
index_name(field_name [(index_length)] [ASC|DESC])
table_name(
column_name
UNIQUE INDEX|KEY [index_name](
field_name [(index_length)] [ASC|DESC])
)
一、CREATE UNIQUE INDEX index_name ON table_name (
field_name [(index_length)] [ASC|DESC])
二、ALTER TABLE table_name ADD UNIQUE INDEX|KEY
index_name(field_name [(index_length)] [ASC|DESC])
table_name(
column_name
FULLTEXT INDEX|KEY [index_name](
field_name [(index_length)] [ASC|DESC])
)
一、CREATE FULLTEXT INDEX index_name ON table_name (
field_name [(index_length)] [ASC|DESC])
二、ALTER TABLE table_name ADD FULLTEXT INDEX|KEY
index_name(field_name [(index_length)] [ASC|DESC])
和上面的方法相似
index_name(field_name_1 [(index_length)] [ASC|DESC],
… ,
field_name_n [(index_length)] [ASC|DESC])
DROP INDEX index_name ON table_name
CREATE VIEW view_name AS select_query
SHOW TABLE STATUS [FROM database_name] [LIKE ‘pattern’]
DESC[RIBE] view_name
DROP VIEW view_name[, view_name]
一、CREATE OR REPLACE VIEW view_name AS select_query
二、ALTER VIEW view_name AS select_query
CREATE TIRGGER trigger_name
BEFORE|AFTER DELETE|INSERT|UPDATE
ON table_name FOR EACH ROW
Triggle_statement
Triggle_statement:触发器被触发要执行的语句(增、删、改、查等等)
SHOW TRIGGERS
DROP TRIGGER trigger_name
INSERT INTO table_name (field_1, field_2, …) VALUES (value_1, value_2, vaule_3, …)
desc 表名;
show columns from 表名;
describe 表名;
show create table 表名;
use information_schema
select * from columns where table_name=’表名’;
select * from userdetail where userid limit 0,20
(mysql-5.5.5开始,InnoDB做为默认存储引擎)以前是MyISAM,更早是ISAM你能用的数据库引擎取决于mysql在安装的时候是如何被编译的。要添加一个新的引擎,就必须从新编译MYSQL。在缺省状况下,MYSQL支持三个引擎:ISAM、MYISAM和HEAP。另外两种类型INNODB和BERKLEYDB(BDB), 也经常能够使用。
ISAM是一个定义明确且历经时间考验的数据表格管理方法,它在设计之时就考虑到数据库被查询的次数要远大于更新的次数。所以,ISAM执行读取操做的速度很快,并且不占用大量的内存和存储资源。ISAM的两个主要不足之处在于,它不支持事务处理,也不可以容错:若是你的硬盘崩溃了,那么数据文件就没法恢复了。若是你正在把ISAM用在关键任务应用程序里,那就必须常常备份你全部的实时数据,经过其复制特性,MYSQL可以支持这样的备份应用 程序。
MYISAM是MYSQL的ISAM扩展格式和缺省的数据库引擎(5.5以前)。除了提供ISAM里所没有的索引和字段管理的大 量功能,MYISAM还使用一种表格锁定的机制,来优化多个并发的读写操做。其代价是你须要常常运行OPTIMIZE TABLE命令,来恢复被更新机制所浪费的空间。MYISAM还有一些有用的扩展,例如用来修复数据库文件的 MYISAMCHK工具和用来恢复浪费空间的MYISAMPACK工具。
MYISAM强调了快速读取操做,这可能就是为何MYSQL受到了WEB开发如此青睐的主要缘由:在WEB开发中你所进行的大量数据操做都是读取操做。因此,大多数虚拟主机提供商和INTERNET平台提供商只容许使用MYISAM格式。
HEAP容许只驻留在内存里的临时表格。驻留在内存使得HEAP比ISAM和MYISAM的速度都快,可是它所管理的数据是不稳定的,并且若是在关机以前没有进行保存,那么全部的数据都会丢失。在数据行被删除的时候,HEAP也不会浪费大量的空间,HEAP表格在你须要使用SELECT表达式来选择和操控数据的时候很是有用。要记住,用完表格后要删除表格。
INNODB和BERKLEYDB(BDB)数据库引擎都是造就MYSQL灵活性的技术的直接产品,这项技术就是MySql++ API。在使用MySql的时候,你所面对的每个挑战几乎都源于ISAM和MYIASM数据库引擎不支持事务处理也不支持外来键。尽管要比ISAM和MYISAM引擎慢不少,可是INNODB和BDB包括了对事务处理和外来键的支持,这两点都是前两个引擎所没有的。如前所述,若是你的设计须要这些特性中的一者或者二者,那你就要被迫使用后两个引擎中的一个了。
根据锁的类型分,能够分为共享锁,排他锁,意向共享锁和意向排他锁。
根据锁的粒度分,又能够分为行锁,表锁。
对于mysql而言,事务机制更可能是靠底层的存储引擎来实现,所以,mysql层面只有表锁,而支持事务的innodb存 储引擎则实现了行锁(记录锁(在行相应的索引记录上的锁)),gap锁(是在索引记录间歇上的锁),next-key锁(是记录锁和在此索引记录以前的gap上的锁的结合)。Mysql的记录锁实质是索引记录的锁,由于innodb是索引组织表;gap锁是索引记录间隙的锁,这种锁只在RR隔离级别下有效;next-key锁是记录锁加上记录以前gap锁的组合。mysql经过gap锁和next-key锁实现RR隔离级别。
说明:对于更新操做(读不上锁),只有走索引才可能上行锁;不然会对聚簇索引的每一行上写锁,实际等同于对表上写锁。
若多个物理记录对应同一个索引,若同时访问,也会出现锁冲突;
当表有多个索引时,不一样事务能够用不一样的索引锁住不一样的行,另外innodb会同时用行锁对数据记录(聚簇索引)加 锁。
MVCC(多版本并发控制)并发控制机制下,任何操做都不会阻塞读操做,读操做也不会阻塞任何操做,只由于读不上锁。
共享锁:由读表操做加上的锁,加锁后其余用户只能获取该表或行的共享锁,不能获取排它锁,也就是说只能读不能写
排它锁:由写表操做加上的锁,加锁后其余用户不能获取该表或行的任何锁,典型是mysql事务中的更新操做
意向共享锁(IS):事务打算给数据行加行共享锁,事务在给一个数据行加共享锁前必须先取得该表的IS锁。
意向排他锁(IX):事务打算给数据行加行排他锁,事务在给一个数据行加排他锁前必须先取得该表的IX锁。
在缺省模式下,MYSQL是autocommit模式的,全部的数据库更新操做都会即时提交,因此在缺省状况下,mysql是不支持事务的。 可是若是你的MYSQL表类型是使用InnoDB Tables 或 BDB tables的话,你的MYSQL就能够使用事务处理,使用SET AUTOCOMMIT=0就能够使MYSQL容许在非autocommit模式, 在非autocommit模式下,你必须使用COMMIT来提交你的更改,或者用ROLLBACK来回滚你的更改。
示例以下:
START TRANSACTION;
SELECT @A:=SUM(salary) FROM table1 WHERE type=1;
UPDATE table2 SET summmary=@A WHERE type=1;
COMMIT;
一、能够处理拥有上千万条记录的大型数据
二、支持常见的SQL语句规范
三、可移植行高,安装简单小巧
四、良好的运行效率,有丰富信息的网络支持
五、调试、管理,优化简单(相对其余大型数据库)
一、在数据库安装的时候指定字符集
二、若是在安完了之后能够更改以配置文件
三、创建数据库时候:指定字符集类型
四、建表的时候也指定字符集
1.若是MYSQL客户端和服务器端的链接须要跨越并经过不可信任的网络,那么须要使用ssh隧道来加密该链接的通讯。
2.使用set password语句来修改用户的密码,先“mysql -u root”登录数据库系统,而后mysql> update mysql.user set password=password(‘newpwd’),最后执行flush privileges就能够了。
3.Mysql须要提防的攻击有,防偷听、篡改、回放、拒绝服务等,不涉及可用性和容错方面。对全部的链接、查询、其余操做使用基于acl即访问控制列表的安全措施来完成。也有一些对ssl链接的支持。
4.设置除了root用户外的其余任何用户不容许访问mysql主数据库中的user表; 加密后存放在user表中的加密 后的用户密码一旦泄露,其余人能够随意用该用户名/密码相应的数据库;
5.使用grant和revoke语句来进行用户访问控制的工做;
6.不要使用明文密码,而是使用md5()和sha1()等单向的哈系函数来设置密码;
7.不要选用字典中的字来作密码;
8.采用防火墙能够去掉50%的外部危险,让数据库系统躲在防火墙后面工做,或放置在dmz区域中;
9.从因特网上用nmap来扫描3306端口,也可用telnet server_host 3306的方法测试,不容许从非信任网络中访问数据库服务器的3306号tcp端口,须要在防火墙或路由器上作设定;
10.为了防止被恶意传入非法参数,例如where id=234,别人却输入where id=234 or 1=1致使所有显示,因此在web的表单中使用”或””来用字符串,在动态url中加入%22表明双引号、%23表明井号、%27表明单引号;传递未检查过的值给mysql数据库是很是危险的;
11.在传递数据给mysql时检查一下大小;
12.应用程序须要链接到数据库应该使用通常的用户账号,开放少数必要的权限给该用户; pagedevidepagedevide
13.在各编程接口(c c++ php perl java jdbc等)中使用特定‘逃脱字符’函数; 在因特网上使用mysql数据 库时必定少用传输明文的数据,而用ssl和ssh的加密方式数据来传输;
14.学会使用tcpdump和strings工具来查看传输数据的安全性,例如tcpdump -l -i eth0 -w -src or
dst port 3306 strings。以普通用户来启动mysql数据库服务;
15.不使用到表的联结符号,选用的参数 –skip-symbolic-links;
16.确信在mysql目录中只有启动数据库服务的用户才能够对文件有读和写的权限;
17.不准将process或super权限付给非管理用户,该mysqladmin processlist能够列举出当前执行的查询 文本;super权限可用于切断客户端链接、改变服务器运行参数状态、控制拷贝复制数据库的服务器;
18.file权限不付给管理员之外的用户,防止出现load data ‘/etc/passwd’到表中再用select 显示出来
的问题;
19.若是不相信dns服务公司的服务,能够在主机名称容许表中只设置ip数字地址;
20.使用max_user_connections变量来使mysqld服务进程,对一个指定账户限定链接数;
21.grant语句也支持资源控制选项;
22.–local-infile=0或1 如果0则客户端程序就没法使用local load data了,赋权的一个例子grant insert(user) on mysql.user to ‘user_name’@’host_name’;若使用–skip-grant-tables系统将对任何用户的访问不作任何访问控制,但能够用 mysqladmin flush-privileges或mysqladmin reload来开启访问控制;默认状况是show databases语句对全部用户开放,能够用–skip-show-databases来关闭掉。
23.碰到error 1045(28000) access denied for user ‘root’@’localhost’ (using password:no)错误时,你须要从新设置密码,具体方法是:先用–skip-grant-tables参数启动mysqld,而后执行 mysql -u root mysql,mysql>update user set password=password(’newpassword’) where user=’root’;mysql>flush privileges;,最后从新启动mysql就能够了。
取得当前时间用 now() 就行。在数据库中格式化时间 用DATE_FORMAT(date, format)。根据格式串
format 格式化日期或日期时间值date,返回结果串。
答案: Debian 上运行命令 service mysql status,在RedHat 上运行命令 service mysqld status。而后看看输出便可。
答案:运行命令 service mysqld start 开启服务;运行命令 service mysqld stop 中止服务。
答案:运行命令 mysql -u root –p
答案:运行命令 show databases;
答案:运行命令 use database_name; 进入名为 database_name 的数据库。
答案:在当前数据库运行命令 show tables;
答案:运行命令 describe table_name;
答案:运行命令 drop table table_name;
对于查询占主要的应用来讲,索引显得尤其重要。不少时候性能问题很简单的就是由于咱们忘了添加索引而形成的,或者说没有添加更为有效的索引致使。若是不加索引的话,那么查找任何哪怕只是一条特定的数据都会进行一次全表扫描,若是一张表的数据量很大而符合条件的结果又不多,那么不加索引会引发致命的性能降低。可是也不是什么情 况都非得建索引不可,好比性别可能就只有两个值,建索引不只没什么优点,还会影响到更新速度,这被称为过分索引。
好比有一条语句是这样的:select * from users where area=’beijing’ and age=22;
若是咱们是在area和age上分别建立单个索引的话,因为mysql查询每次只能使用一个索引,因此虽然这样已经相对不作索引时全表扫描提升了不少效率,可是若是在area、age两列上建立复合索引的话将带来更高的效率。若是咱们建立了(area, age, salary)的复合索引,那么其实至关于建立了(area,age,salary)、 (area,age)、(area)三个索引,这被称为最佳左前缀特性。所以咱们在建立复合索引时应该将最经常使用做限制条件的列放在最左边,依次递减。
只要列中包含有NULL值都将不会被包含在索引中,复合索引中只要有一列含有NULL值,那么这一列对于此复合索引就是无效的。因此咱们在数据库设计时不要让字段的默认值为NULL。
对串列进行索引,若是可能应该指定一个前缀长度。例如,若是有一个CHAR(255)的列,若是在前10个或20个字符内,多数值是唯一的,那么就不要对整个列进行索引。短索引不只能够提升查询速度并且能够节省磁盘空间和I/O操做。
mysql查询只使用一个索引,所以若是where子句中已经使用了索引的话,那么order by中的列是不会使用索引的。所以数据库默认排序能够符合要求的状况下不要使用排序操做;尽可能不要包含多个列的排序,若是须要最好给这些列建立复合索引。
通常状况下不鼓励使用like操做,若是非使用不可,如何使用也是一个问题。like “%aaa%” 不会使用索引而like “aaa%”能够使用索引。
VARCHAR和CHAR类型,varchar是变长的,须要额外的1-2个字节存储,能节约空间,可能会对性能有帮助。但因为是变长,可能发生碎片,如更新数据;
使用ENUM(MySQL的枚举类)代替字符串类型,数据实际存储为整型。
字符串类型
要尽量地避免使用字符串来作标识符,由于它们占用了不少空间而且一般比整数类型要慢。特别注意不要在MYISAM表上使用字符串标识符。MYISAM默认状况下为字符串使用了压缩索引(Packed Index),这使查找更为缓慢。据测试,使用了压缩索引的MYISAM表性能要慢6倍。
还要特别注意彻底‘随机’的字符串,例如由MD5()、SHA1()、UUID()产生的。它们产生的每个新值都会被任意地保存在很大的空间范围内,这会减慢INSERT及一些SELECT查询。1)它们会减慢INSERT查询,由于插入的值会被随机地放入索引中。这会致使分页、随机磁盘访问及汇集存储引擎上的汇集索引碎片。2)它们会减慢SELECT查询,由于逻辑上相邻的行会分布在磁盘和内存中的各个地方。3)随机值致使缓存对全部类型的查询性能都不好,由于它们会使缓存赖以工做的访问局部性失效。若是整个数据集都变得一样“热”的时候,那么把特定部分的数据缓存到内存中就没有任何的优点了。而且若是工做集不能被装入内存中,缓存就会进行不少刷写的工做,而且会致使不少缓存未命中。
若是保存UUID值,就应该移除其中的短横线,更好的办法是使用UHEX()把UUID值转化为16字节的数字,并把它保存在BINARY(16)列中。
select * from users where YEAR(adddate)<2007;
将在每一个行上进行运算,这将致使索引失效而进行全表扫描,所以咱们能够改为
select * from users where adddate<‘2007-01-01’;
不使用NOT IN和操做
NOT IN和操做都不会使用索引将进行全表扫描。NOT IN能够NOT EXISTS代替,id != 3则可以使用id>3 or id<3来代替。
不能用null做索引,任何包含null值的列都将不会被包含在索引中。即便索引有多列这样的状况下,只要这些列中有一列含有null,该列就会从索引中排除。也就是说若是某列存在空值,即便对该列建索引也不会提升性能。
任何在where子句中使用is null或is not null的语句优化器是不容许使用索引的。
对于有联接的列,即便最后的联接值为一个静态值,优化器是不会使用索引的。
一、逻辑备份:使用mysql自带的mysqldump工具进行备份。备份成sql文件形式。
优势:最大好处是可以与正在运行的mysql自动协同工做,在运行期间能够确保备份是当时的点,它会自动将对应操做的表锁定,不容许其余用户修改(只能访问)。可能会阻止修改操做。sql文件通用方便移植。
缺点:备份的速度比较慢。若是是数据量不少的时候。就很耗时间。若是数据库服务器处在提供给用户服务状态,在这段长时间操做过程当中,意味着要锁定表(通常是读锁定,只能读不能写入数据)。那么服务就会影响的。
二、物理备份:直接拷贝mysql的数据目录。
直接拷贝只适用于myisam类型的表。这种类型的表是与机器独立的。但实际状况是,你设计数据库的时候不可能所有使用myisam类型表。你也不可能由于myisam类型表与机器独立,方便移植,因而就选择这种表,这并非选择它的理由。
缺点:你不能去操做正在运行的mysql服务器(在拷贝的过程当中有用户经过应用程序访问更新数据,这样就没法备份当时的数据)可能没法移植到其余机器上去。
三、双机热备份。
mysql数据库没有增量备份的机制。当数据量太大的时候备份是一个很大的问题。还好mysql数据库提供了一种主从备份的机制(也就是双机热备)
优势:适合数据量大的时候。如今明白了。大的互联网公司对于mysql数据备份,都是采用热机备份。搭建多台数据库服务器,进行主从复制。
explain显示了mysql如何使用索引来处理select语句以及链接表。能够帮助选择更好的索引和写出更优化的查询语句。使用方法,在select语句前加上explain就能够了。因此使用explain能够查看。
能够使用逻辑备份和双机热备份。
彻底备份:完整备份通常一段时间进行一次,且在网站访问量最小的时候,这样常借助批处理文件定时备份。主要是写一个批处理文件在里面写上处理程序的绝对路径而后把要处理的东西写在后面,即彻底备份数据库。
增量备份:对ddl和dml语句进行二进制备份。且5.0没法增量备份,5.1后能够。若是要实现增量备份须要在my.ini文件中配置备份路径便可,重启mysql服务器,增量备份就启动了。
普通索引 添加INDEX
ALTER TABLE ‘table_name’ ADD INDEX index_name (‘column’);
主键索引 添加PRIMARY KEY
ALTER TABLE ‘table_name’ ADD PRIMARY KEY (‘column’);
惟一索引 添加UNIQUE
ALTER TABLE ‘table_name’ ADD UNIQUE (‘column’);
全文索引 添加FULLTEXT
ALTER TABLE ‘table_name’ ADD FULLTEXT (‘column’);
多列索引
ALTER TABLE ‘table_name’ ADD INDEX index_name (‘column1’, ‘column2’, ‘column3’)
表的主关键字
自动创建惟一索引
如zl_yhjbqk(用户基本状况)中的hbs_bh(户标识编号)
表的字段惟一约束
ORACLE利用索引来保证数据的完整性
如lc_hj(流程环节)中的lc_bh+hj_sx(流程编号+环节顺序)
直接条件查询的字段
在SQL中用于条件约束的字段
如zl_yhjbqk(用户基本状况)中的qc_bh(区册编号)
select * from zl_yhjbqk where qc_bh=’7001’
查询中与其它表关联的字段
字段经常创建了外键关系
如zl_ydcf(用电成份)中的jldb_bh(计量点表编号)
select * from zl_ydcf a,zl_yhdb b where a.jldb_bh=b.jldb_bh and b.jldb_bh=’540100214511’
查询中排序的字段
排序的字段若是经过索引去访问那将大大提升排序速度
select * from zl_yhjbqk order by qc_bh(创建qc_bh索引)
select * from zl_yhjbqk where qc_bh=’7001’ order by cb_sx(创建qc_bh+cb_sx索引,注:只是一个索引,其中包括qc_bh和cb_sx字段)
查询中统计或分组统计的字段
select max(hbs_bh) from zl_yhjbqk
select qc_bh,count(*) from zl_yhjbqk group by qc_bh
表记录太少
若是一个表只有5条记录,采用索引去访问记录的话,那首先需访问索引表,再经过索引表访问数据表,通常索引表与数据表不在同一个数据块,这种状况下ORACLE至少要往返读取数据块两次。而不用索引的状况下ORACLE会将全部的数据一次读出,处理速度显然会比用索引快。
如表zl_sybm(使用部门)通常只有几条记录,除了主关键字外对任何一个字段建索引都不会产生性能优化,实际上若是对这个表进行了统计分析后ORACLE也不会用你建的索引,而是自动执行全表访问。如:select * from zl_sybm where sydw_bh=’5401’(对sydw_bh创建索引不会产生性能优化)
常常插入、删除、修改的表
对一些常常处理的业务表应在查询容许的状况下尽可能减小索引,如zl_yhbm,gc_dfss,gc_dfys,gc_fpdy等业务表。
数据重复且分布平均的表字段
假如一个表有10万行记录,有一个字段A只有T和F两种值,且每一个值的分布几率大约为50%,那么对这种表A字段建索引通常不会提升数据库的查询速度。
常常和主字段一块查询但主字段索引值比较多的表字段
如gc_dfss(电费实收)表常常按收费序号、户标识编号、抄表日期、电费发生年月、操做 标志来具体查询某一笔收款的状况,若是将全部的字段都建在一个索引里那将会增长数据的修改、插入、删除时间,从实际上分析一笔收款若是按收费序号索引就已 经将记录减小到只有几条,若是再按后面的几个字段索引查询将对性能不产生太大的影 响。
1.对查询进行优化,应尽可能避免全表扫描,首先应考虑在 where 及 order by 涉及的列上创建索引。
2.应尽可能避免在 where 子句中对字段进行 null 值判断,不然将致使引擎放弃使用索引而进行全表扫描,如:select id from t where num is null能够在num上设置默认值0,确保表中num列没有null值,而后这样查询:select id from t where num=0
3.应尽可能避免在 where 子句中使用!=或<>操做符,不然引擎将放弃使用索引而进行全表扫描。
4.应尽可能避免在 where 子句中使用or 来链接条件,不然将致使引擎放弃使用索引而进行全表扫描,如:select id from t where num=10 or num=20能够这样查询:select id from t where num=10 union all select id from t where num=20
5.in 和 not in 也要慎用,不然会致使全表扫描,如:select id from t where num in(1,2,3) 对于连续的数值,能用 between 就不要用 in 了:select id from t where num between 1 and 3
6.避免使用通配符。下面的查询也将致使全表扫描:select id from t where name like ‘李%’若要提升效率,能够考虑全文检索。
7.若是在 where 子句中使用参数,也会致使全表扫描。由于SQL只有在运行时才会解析局部变量,但优化程序不能将访问计划的选择推迟到运行时;它必须在编译时进行选择。然而,若是在编译时创建访问计划,变量的值仍是未知的,于是没法做为索引选择的输入项。以下面语句将进行全表扫描:select id from t where num=@num能够改成强制查询使用索引:select id from t with(index(索引名)) where num=@num
8.应尽可能避免在 where 子句中对字段进行表达式操做,这将致使引擎放弃使用索引而进行全表扫描。如:select id from t where num/2=100应改成:select id from t where num=100*2
9.应尽可能避免在where子句中对字段进行函数操做,这将致使引擎放弃使用索引而进行全表扫描。如:select id from t where substring(name,1,3)=’abc’ ,name以abc开头的id应改成:select id from t where name like ‘abc%’
10.不要在 where 子句中的“=”左边进行函数、算术运算或其余表达式运算,不然系统将可能没法正确使用索引。
11.在使用索引字段做为条件时,若是该索引是复合索引,那么必须使用到该索引中的第一个字段做为条件时才能保证系统使用该索引,不然该索引将不会被使用,而且应尽量的让字段顺序与索引顺序相一致。
12.不要写一些没有意义的查询,如须要生成一个空表结构:select col1,col2 into #t from t where 1=0 这类代码不会返回任何结果集,可是会消耗系统资源的,应改为这样:create table #t(…)
13.不少时候用 exists 代替 in 是一个好的选择:select num from a where num in(select num from b)用下面的语句替换:select num from a where exists(select 1 from b where num=a.num)
14.并非全部索引对查询都有效,SQL是根据表中数据来进行查询优化的,当索引列有大量数据重复时,SQL查询可能不会去利用索引,如一表中有字段sex,male、female几乎各一半,那么即便在sex上建了索引也对查询效率起不了做用。
15.索引并非越多越好,索引当然能够提升相应的 select 的效率,但同时也下降了insert 及 update 的 效率,由于 insert 或 update 时有可能会重建索引,因此怎样建索引须要慎重考虑,视具体状况而定。一个表的索引数最好不要超过6个,若太多则应考虑一些不常使用到的列上建的索引是否有 必要。
16.应尽量的避免更新 clustered 索引数据列,由于 clustered 索引数据列的顺序就是表记录的物理存储 顺序,一旦该列值改变将致使整个表记录的顺序的调整,会耗费至关大的资源。若应用系统须要频繁更新 clustered 索引数据列,那么须要考虑是否应将该索引建为 clustered 索引。
17.尽可能使用数字型字段,若只含数值信息的字段尽可能不要设计为字符型,这会下降查询和链接的性能,并会增长存储开销。这是由于引擎在处理查询和链接时会逐个比较字符串中每个字符,而对于数字型而言只须要比较一次就够了。
18.尽量的使用 varchar/nvarchar 代替 char/nchar ,由于首先变长字段存储空间小,能够节省存储空间,其次对于查询来讲,在一个相对较小的字段内搜索效率显然要高些。
19.任何地方都不要使用 select * from t ,用具体的字段列表代替“*”,不要返回用不到的任何字段。
20.尽可能使用表变量来代替临时表。若是表变量包含大量数据,请注意索引很是有限(只有主键索引)。
21.避免频繁建立和删除临时表,以减小系统表资源的消耗。
22.临时表并非不可以使用,适当地使用它们能够使某些例程更有效,例如,当须要重复引用大型表或经常使用表中的某个数据集时。可是,对于一次性事件,最好使用导出表。
23.在新建临时表时,若是一次性插入数据量很大,那么能够使用 select into 代替 create table,避免形成大量 log ,以提升速度;若是数据量不大,为了缓和系统表的资源,应先create table,而后insert。
24.若是使用到了临时表,在存储过程的最后务必将全部的临时表显式删除,先 truncate table ,而后 drop table ,这样能够避免系统表的较长时间锁定。
25.尽可能避免使用游标,由于游标的效率较差,若是游标操做的数据超过1万行,那么就应该考虑改写。
26.使用基于游标的方法或临时表方法以前,应先寻找基于集的解决方案来解决问题,基于集的方法一般更有效。
27.与临时表同样,游标并非不可以使用。对小型数据集使用 FAST_FORWARD 游标一般要优于其余逐行处理方法,尤为是在必须引用几个表才能得到所需的数据时。在结果集中包括“合计”的例程一般要比使用游标执行的速度快。若是开发时间容许,基于游标的方法和基于集的方法均可以尝试一下,看哪种方法的效果更好。
28.在全部的存储过程和触发器的开始处设置 SET NOCOUNT ON ,在结束时设置 SET NOCOUNT OFF。无需在执行存储过程和触发器的每一个语句后向客户端发送DONE_IN_PROC 消息。
29.尽可能避免大事务操做,提升系统并发能力。
30.尽可能避免向客户端返回大数据量,若数据量过大,应该考虑相应需求是否合理。
1,建立索引
对于查询占主要的应用来讲,索引显得尤其重要。不少时候性能问题很简单的就是由于咱们忘了添加索引而形成的,或者说没有添加更为有效的索引致使。若是不加索引的话,那么查找任何哪怕只是一条特定的数据都会进行一次全表扫描,若是一张表的数据量很大而符合条件的结果又不多,那么不加索引会引发致命的性能降低。可是也不是什么状况都非得建索引不可,好比性别可能就只有两个值,建索引不只没什么优点,还会影响到更新速度,这被称为过分索引。
2,复合索引
好比有一条语句是这样的:select * from users where area=’beijing’ and age=22;
若是咱们是在area和age上分别建立单个索引的话,因为mysql查询每次只能使用一个索引,因此虽然这样已经相对不作索引时全表扫描提升了不少效率,可是若是在area、age两列上建立复合索引的话将带来更高的效率。若是咱们建立了(area, age,salary)的复合索引,那么其实至关于建立了(area,age,salary)、(area,age)、(area)三个索引,这被称为最佳左前缀特性。所以咱们在建立复合索引时应该将最经常使用做限制条件的列放在最左边,依次递减。
3,索引不会包含有NULL值的列
只要列中包含有NULL值都将不会被包含在索引中,复合索引中只要有一列含有NULL值,那么这一列对于此复合索引就是无效的。因此咱们在数据库设计时不要让字段的默认值为NULL。
4,使用短索引
对串列进行索引,若是可能应该指定一个前缀长度。例如,若是有一个CHAR(255)的 列,若是在前10 个或20 个字符内,多数值是唯一的,那么就不要对整个列进行索引。短索引不只能够提升查询速度并且能够节省磁盘空间和I/O操做。
5,排序的索引问题
mysql查询只使用一个索引,所以若是where子句中已经使用了索引的话,那么order by中的列是不会使用索引的。所以数据库默认排序能够符合要求的状况下不要使用排序操做;尽可能不要包含多个列的排序,若是须要最好给这些列建立复合索引。
6,like语句操做
通常状况下不鼓励使用like操做,若是非使用不可,如何使用也是一个问题。like “%aaa%” 不会使用索引而like “aaa%”能够使用索引。
7,不要在列上进行运算
select * from users where YEAR(adddate)
8,不使用NOT IN和操做
NOT IN和操做都不会使用索引将进行全表扫描。NOT IN能够NOT EXISTS代替,id != 3则可以使用id>3 or id < 3
一、show processlist;
二、select * from information_schema.processlist ;
三、能够在[mysqld]中添加以下:
log =/var/log/mysql.log
若是须要监控慢查询能够添加以下内容:
log-slow-queries = /var/log/slowquery.log
long_query_time = 1
术语“汇集”指实际的数据行和相关的键值都保存在一块儿。每一个表只能有一个汇集索引。可是,覆盖索引能够模拟多个汇集索引。存储引擎负责实现索引,所以不是全部的存储索引都支持汇集索引。当前,SolidDB和InnoDB是惟一支持汇集索引的存储引擎。
优势:
能够把相关数据保存在一块儿。这样从磁盘上提取几个页面的数据就能把某个用户的数据所有抓取出来。若是没有使用汇集,读取每一个数据都会访问磁盘。
数据访问快。汇集索引把索引和数据都保存到了同一棵B-TREE中,所以从汇集索引中取得数据一般比在非汇集索引进行查找要快。
缺点:
汇集能最大限度地提高I/O密集负载的性能。若是数据能装入内存,那么其顺序也就无所谓了。这样汇集就没有什么用处。
插入速度严重依赖于插入顺序。更新汇集索引列是昂贵的,由于强制InnoDB把每一个更新的行移到新的位置。
创建在汇集索引上的表在插入新行,或者在行的主键被更新,该行必须被移动的时候会进行分页。
汇集表可会比全表扫描慢,尤为在表存储得比较稀疏或由于分页而没有顺序存储的时候。
第二(非汇集)索引可能会比预想的大,由于它们的叶子节点包含了被引用行的主键列。第二索引访问须要两次索引查找,而不是一次。 InnoDB的第二索引叶子节点包含了主键值做为指向行的“指针”,而不是“行指针”。 这种策略减小了在移动行或数据分页的时候索引的维护工做。使用行的主键值做为指针使得索引变得更大,可是这意味着InnoDB能够移动行,而无须更新指针。
索引类型: B-TREE索引,哈希索引
B-TREE索引(默认的索引类型)加速了数据访问,由于存储引擎不会扫描整个表获得须要的数据。相反,它从根节点开始。根节点保存了指向子节点的指针,而且存储引擎会根据指针寻找数据。它经过查找节点页中的值找到正确的指针,节点页包含子节点的指针,而且存储引擎会根据指针寻找数据。它经过查找节点页中的值找到正确的指针,节点页包含子节点中值的上界和下界。最后,存储引擎可能没法找到须要的数据,也可能成功地找到包含数据的叶子页面。
例:B-TREE索引 对于如下类型查询有用。匹配全名、匹配最左前缀、匹配列前缀、匹配范围值、精确匹配一部分而且匹配某个范围中的另外一部分;
B-TREE索引的局限:若是查找没有从索引列的最左边开始,它就没什么用处。不能跳过索引中的列,存储引擎不能优先访问任何在第一个范围条件右边的列。例:若是查询是where last_name=’Smith’ AND first_name LIKE ‘J%’ AND dob=’1976-12-23’;访问就只能使用索引的头两列,由于LIKE是范围条件。
哈希索引创建在哈希表的基础上,它只对使用了索引中的每一列的精确查找有用。对于每一行,存储引擎计算出了被索引列的哈希码,它是一个较小的值,而且有可能和其余行的哈希码不一样。它把哈希码保存在索引中,而且保存了一个指向哈希表中每一行的指针。
由于索引只包含了哈希码和行指针,而不是值自身,MYSQL不能使用索引中的值来避免读取行。
MYSQL不能使用哈希索引进行排序,由于它们不会按序保存行。
哈希索引不支持部分键匹配,由于它们是由被索引的所有值计算出来的。也就是说,若是在(A,B)两列上有索引,而且WHERE子句中只使用了A,那么索引就不会起做用。
哈希索引只支持使用了= IN()和<=>的相等比较。它们不能加快范围查询。例如WHERE price > 100;
访问哈希索引中的数据很是快,除非碰撞率很高。当发生碰撞的时候,存储引擎必须访问链表中的每个行指针,而后逐行进行数据比较,以肯定正确的数据。若是有不少碰撞,一些索引维护操做就有可能会变慢。
即为全文索引,目前只有MyISAM引擎支持。其能够在CREATE TABLE ,ALTER TABLE ,CREATE INDEX 使用,不过目前只有 CHAR、VARCHAR ,TEXT 列上能够建立全文索引。值得一提的是,在数据量较大时候,现将数据放入一个没有全局索引的表中,而后再用CREATE INDEX建立FULLTEXT索引,要比先为一张表创建FULLTEXT而后再将数据写入的速度快不少。FULLTEXT索引也是按照分词原理创建索引的。西文中,大部分为字母文字,分词能够很方便的按照空格进行分割。中文不能按照这种方式进行分词。Mysql的中文分词插件Mysqlcft,有了它,就能够对中文进行分词。
1、在编译时优化MySQL
若是你从源代码分发安装MySQL,要注意,编译过程对之后的目标程序性能有重要的影响,不一样的编译方式可能获得相似的目标文件,但性能可能相差很大,所以,在编译安装MySQL适应仔细根据你的应用类型选择最可能好的编译选项。这种定制的MySQL能够为你的应用提供最佳性能。
技巧:选用较好的编译器和较好的编译器选项,这样应用可提升性能10-30%。(MySQL文档如是说)
1.一、使用pgcc(Pentium GCC)编译器->(使用合适的编译器)
该编译器(http://www.goof.com/pcg/)针对运行在奔腾处理器系统上的程序进行优化,用pgcc编译MySQL源代码,整体性能可提升10%。固然若是你的服务器不是用奔腾处理器,就没必要用它了,由于它是专为奔腾系统设计的。
1.二、仅使用你想使用的字符集编译MySQL
MySQL目前提供多达24种不一样的字符集,为全球用户以他们本身的语言插入或查看表中的数据。却省状况下,MySQL安装全部者这些字符集,热然而,最好的选择是指选择一种你须要的。如,禁止除Latin1字符集之外的全部其它字符集:
1.三、将mysqld编译成静态执行文件
将mysqld编译成静态执行文件而无需共享库也能得到更好的性能。经过在配置时指定下列选项,可静态编译mysqld。
1.四、配置样本
2、调整服务器
3、表类型(MySQL中表的类型)
不少MySQL用户可能很惊讶,MySQL确实为用户提供5种不一样的表类型,称为DBD、HEAP、ISAM、MERGE和MyIASM。DBD归为事务安全类,而其余为非事务安全类。
3.一、事务安全
DBD
Berkeley DB(DBD)表是支持事务处理的表,它提供MySQL用户期待已久的功能-事务控制。事务控制在任何数据库系统中都是一个极有价值的功能,由于它们确保一组命令能成功地执行。
3.二、非事务安全
HEAP
HEAP表是MySQL中存取数据最快的表。这是由于他们使用存储在动态内存中的一个哈希索引。另外一个要点是若是MySQL或服务器崩溃,数据将丢失。
ISAM
ISAM表是早期MySQL版本的缺省表类型,直到MyIASM开发出来。建议不要再使用它。
MERGE
MERGE是一个有趣的新类型,在3.23.25以后出现。一个MERGE表其实是一个相同MyISAM表的集合,合并成一个表,主要是为了效率缘由。这样能够提升速度、搜索效率、修复效率并节省磁盘空间。
MyIASM
这是MySQL的缺省表类型(5.5.5以前)。它基于IASM代码,但有不少有用的扩展。MyIASM比较好的缘由:
MyIASM表小于IASM表,因此使用较少资源。
MyIASM表在不一样的平台上二进制层可移植。
更大的键码尺寸,更大的键码上限。
3.三、指定表类型
4、优化工具
MySQL服务器自己提供了几条内置命令用于帮助优化。
4.一、SHOW
SHOW还能作更多的事情。它能够显示关于日志文件、特定数据库、表、索引、进程和权限表中有价值的信息。
4.二、EXPLAIN
当你面对SELECT语句时,EXPLAIN解释SELECT命令如何被处理。这不只对决定是否应该增长一个索引,并且对决定一个复杂的Join如何被MySQL处理都是有帮助的。
4.三、OPTIMIZE
OPTIMIZE语句容许你恢复空间和合并数据文件碎片,对包含变长行的表进行了大量更新和删除后,这样作特别重要。OPTIMIZE目前只工做于MyIASM和BDB表。
innodb_buffer_pool_size:这是你安装完InnoDB后第一个应该设置的选项。缓冲池是数据和索引缓存的地方:这个值越大越好,这能保证你在大多数的读取操做时使用的是内存而不是硬盘。典型的值是5-6GB(8GB内存),20-25GB(32GB内存),100-120GB(128GB内存)。
innodb_log_file_size:这是redo日志的大小。redo日志被用于确保写操做快速而可靠而且在崩溃时恢复。一直到MySQL 5.1,它都难于调整,由于一方面你想让它更大来提升性能,另外一方面你想让它更小来使得崩溃后更快恢复。幸运的是从MySQL 5.5以后,崩溃恢复的性能的到了很大提高,这样你就能够同时拥有较高的写入性能和崩溃恢复性能了。一直到MySQL 5.5,redo日志的总尺寸被限定在4GB(默承认以有2个log文件)。这在MySQL 5.6里被提升。
一开始就把innodb_log_file_size设置成512M(这样有1GB的redo日志)会使你有充裕的写操做空间。若是你知道你的应用程序须要频繁的写入数据而且你使用的时MySQL 5.6,你能够一开始就把它这是成4G。max_connections:若是你常常看到‘Too many connections’错误,是由于max_connections的值过低了。这很是常见由于应用程序没有正确的关闭数据库链接,你须要比默认的151链接数更大的值。max_connection值被设高了(例如1000或更高)以后一个主要缺陷是当服务器运行1000个或更高的活动事务时会变的没有响应。在应用程序里使用链接池或者在MySQL里使用进程池有助于解决这一问题。
InnoDB配置
从MySQL 5.5版本开始,InnoDB就是默认的存储引擎而且它比任何其余存储引擎的使用都要多得多。那也是为何它须要当心配置的缘由。
innodb_file_per_table:这项设置告知InnoDB是否须要将全部表的数据和索引存放在共享表空间里 (innodb_file_per_table = OFF)或者为每张表的数据单独放在一个.ibd文件(innodb_file_per_table = ON)。每张表一个文件容许你在drop、truncate或者rebuild表时回收磁盘空间。这对于一些高级特性也是有必要的,好比数据压缩。可是它不会带来任何性能收益。你不想让每张表一个文件的主要场景是:有很是多的表(好比10k+)。
MySQL 5.6中,这个属性默认值是ON,所以大部分状况下你什么都不须要作。对于以前的版本你必需在加载数据以前将这个属性设置为ON,由于它只对新建立的表有影响。
innodb_flush_log_at_trx_commit:默认值为1,表示InnoDB彻底支持ACID特性。当你的主要关注点是数据安全的时候这个值是最合适的,好比在一个主节点上。可是对于磁盘(读写)速度较慢的系统,它会带来很巨大的开销,由于每次将改变flush到redo日志都须要额外的fsyncs。将它的值设置为2会致使不太可靠(reliable)由于提交的事务仅仅每秒才flush一次到redo日志,但对于一些场景是能够接受的,好比对于主节点的备份节点这个值是能够接受的。若是值为0速度就更快了,但在系统崩溃时可能丢失一些数据:只适用于备份节点。
innodb_flush_method: 这项配置决定了数据和日志写入硬盘的方式。通常来讲,若是你有硬件RAID控制器,而且其独立缓存采用write-back机制,并有着电池断电保护,那么应该设置配置为O_DIRECT;不然,大多数状况下应将其设为fdatasync(默认值)。sysbench是一个能够帮助你决定这个选项的好工具。
innodb_log_buffer_size: 这项配置决定了为还没有执行的事务分配的缓存。其默认值(1MB)通常来讲已经够用了,可是若是你的事务中包含有二进制大对象或者大文本字段的话,这点缓存很快就会被填满并触发额外的I/O操做。看看Innodb_log_waits状态变量,若是它不是0,增长innodb_log_buffer_size。
其余设置
query_cache_size: query cache(查询缓存)是一个众所周知的瓶颈,甚至在并发并很少的时候也是如此。 最佳选项是将其从一开始就停用,设置query_cache_size = 0(如今MySQL 5.6的默认值)并利用其余方法加速查询:优化索引、增长拷贝分散负载或者启用额外的缓存(好比memcache或redis)。若是你已经为你的应用启用了query cache而且尚未发现任何问题,query cache可能对你有用。这是若是你想停用它,那就得当心了。
log_bin:若是你想让数据库服务器充当主节点的备份节点,那么开启二进制日志是必须的。若是这么作了以后,还别忘了设置server_id为一个惟一的值。就算只有一个服务器,若是你想作基于时间点的数据恢复,这(开启二进制日志)也是颇有用的:从你最近的备份中恢复(全量备份),并应用二进制日志中的修改(增量备份)。二进制日志一旦建立就将永久保存。因此若是你不想让磁盘空间耗尽,你能够用 PURGE BINARY LOGS 来清除旧文件,或者设置 expire_logs_days 来指定过多少天日志将被自动清除。
记录二进制日志不是没有开销的,因此若是你在一个非主节点的复制节点上不须要它的话,那么建议关闭这个选项。
skip_name_resolve:当客户端链接数据库服务器时,服务器会进行主机名解析,而且当DNS很慢时,创建链接也会很慢。所以建议在启动服务器时关闭skip_name_resolve选项而不进行DNS查找。惟一的局限是以后GRANT语句中只能使用IP地址了,所以在添加这项设置到一个已有系统中必须格外当心。
I 硬件配置优化
Ø CPU选择:多核的CPU,主频高的CPU
Ø 内存:更大的内存
Ø 磁盘选择:更快的转速、RAID、阵列卡,
Ø 网络环境选择:尽可能部署在局域网、SCI、光缆、千兆网、双网线提供冗余、0.0.0.0多端口绑定监听
II操做系统级优化
Ø 使用64位的操做系统,更好的使用大内存。
Ø 设置noatime,nodiratime
Ø 优化内核参数
Ø 加大文件描述符限制
Ø 文件系统选择 xfs
III Mysql设计优化
III.1 存储引擎的选择
Ø Myisam:数据库并发不大,读多写少,并且都能很好的用到索引,sql语句比较简单的应用,TB数据仓库
Ø Innodb:并发访问大,写操做比较多,有外键、事务等需求的应用,系统内存较大。
III.2 命名规则
Ø 多数开发语言命名规则:好比MyAdress
Ø 多数开源思想命名规则:my_address
Ø 避免随便命名
III.3 字段类型选择
字段类型的选择的通常原则:
Ø 根据需求选择合适的字段类型,在知足需求的状况下字段类型尽量小。
Ø 只分配知足需求的最小字符数,不要太慷慨。 缘由:更小的字段类型更小的字符数占用更少的内存,占用更少的磁盘空间,占用更少的磁盘IO,以及占用更少的带宽。
对于varchar和char的选择要根据引擎和具体状况的不一样来选择,主要依据以下原则:
1.若是列数据项的大小一致或者相差不大,则使用char。
2.若是列数据项的大小差别至关大,则使用varchar。
3.对于MyISAM表,尽可能使用Char,对于那些常常须要修改而容易造成碎片的myisam和isam数据表就更是如此,它的缺点就是占用磁盘空间。
4.对于InnoDB表,由于它的数据行内部存储格式对固定长度的数据行和可变长度的数据行不加区分(全部数据行共用一个表头部分,这个标头部分存放着指向各有关数据列的指针),因此使用char类型不见得会比使用varchar类型好。事实上,由于char类型一般要比varchar类型占用更多的空间,因此从减小空间占用量和减小磁盘i/o的角度,使用varchar类型反而更有利。
5.表中只要存在一个varchar类型的字段,那么全部的char字段都会自动变成varchar类型,所以建议定长和变长的数据分开。
III.4 编码选择
单字节 latin1
多字节 utf8(汉字占3个字节,英文字母占用一个字节)若是含有中文字符的话最好都统一采用utf8类型,避免乱码的状况发生。
III.5 主键选择原则
注:这里说的主键设计主要是针对INNODB引擎
1.能惟一的表示行。
2.显式的定义一个数值类型自增字段的主键,这个字段能够仅用于作主键,不作其余用途。
3.MySQL主键应该是单列的,以便提升链接和筛选操做的效率。
4.主键字段类型尽量小,能用SMALLINT就不用INT,能用INT就不用BIGINT。
5.尽可能保证不对主键字段进行更新修改,防止主键字段发生变化,引起数据存储碎片,下降IO性能。
6.MySQL主键不该包含动态变化的数据,如时间戳、建立时间列、修改时间列等。
7.MySQL主键应当有计算机自动生成。
8.主键字段放在数据表的第一顺序。
推荐采用数值类型作主键并采用auto_increment属性让其自动增加。
III.6 其余须要注意的地方
Ø NULL OR NOT NULL
尽量设置每一个字段为NOT NULL,除非有特殊的需求,缘由以下:
1.使用含有NULL列作索引的话会占用更多的磁盘空间,由于索引NULL列须要而外的空间来保存。
2.进行比较的时候,程序会更复杂。
3.含有NULL的列比较特殊,SQL难优化,若是是一个组合索引,那么这个NULL 类型的字段会极大影响整个索引的效率。
Ø 索引
索引的优势:极大地加速了查询,减小扫描和锁定的数据行数。
索引的缺点:占用磁盘空间,减慢了数据更新速度,增长了磁盘IO。
添加索引有以下原则:
1 选择惟一性索引。
2.为常常须要排序、分组和联合操做的字段创建索引。
3.为常做为查询条件的字段创建索引。
4.限制索引的数据,索引不是越多越好。
5.尽可能使用数据量少的索引,对于大字段能够考虑前缀索引。
6.删除再也不使用或者不多使用的索引。
7.结合核心SQL优先考虑覆盖索引。
8.忌用字符串作主键。
Ø 反范式设计
适当的使用冗余的反范式设计,以空间换时间有的时候会很高效。
IV Mysql软件优化
Ø 开启mysql复制,实现读写分离、负载均衡,将读的负载分摊到多个从服务器上,提升服务器的处理能力。
Ø 使用推荐的GA版本,提高性能
Ø 利用分区新功能进行大数据的数据拆分
V Mysql配置优化
注意:全局参数一经设置,随服务器启动预占用资源。
Ø key_buffer_size参数
mysql索引缓冲,若是是采用myisam的话要重点设置这个参数,根据(key_reads/key_read_requests)判断
Ø innodb_buffer_pool_size参数
INNODB 数据、索引、日志缓冲最重要的引擎参数,根据(hit riatos和FILE I/O)判断
Ø wait_time_out参数
线程链接的超时时间,尽可能不要设置很大,推荐10s
Ø max_connections参数
服务器容许的最大链接数,尽可能不要设置太大,由于设置太大的话容易致使内存溢出
Ø thread_concurrency参数
线程并发利用数量,(cpu+disk)*2,根据(os中显示的请求队列和tickets)判断
Ø sort_buffer_size参数
得到更快的–ORDER BY,GROUP BY,SELECT DISTINCT,UNION DISTINCT
Ø read_rnd_buffer_size参数
当根据键进行分类操做时得到更快的–ORDER BY
Ø join_buffer_size参数
join链接使用全表扫描链接的缓冲大小,根据select_full_join判断
Ø read_buffer_size参数
全表扫描时为查询预留的缓冲大小,根据select_scan判断
Ø tmp_table_size参数
临时内存表的设置,若是超过设置就会转化成磁盘表,根据参数(created_tmp_disk_tables)判断
Ø innodb_log_file_size参数(默认5M)
记录INNODB引擎的redo log文件,设置较大的值意味着较长的恢复时间。
Ø innodb_flush_method参数(默认fdatasync)
Linux系统能够使用O_DIRECT处理数据文件,避免OS级别的cache,O_DIRECT模式提升数据文件和日志文件的IO提交性能
Ø innodb_flush_log_at_trx_commit(默认1)
1.0表示每秒进行一次log写入cache,并flush log到磁盘。
2.1表示在每次事务提交后执行log写入cache,并flush log到磁盘。
3.2表示在每次事务提交后,执行log数据写入到cache,每秒执行一次flush log到磁盘。
VI Mysql语句级优化
1.性能查的读语句,在innodb中统计行数,建议另外弄一张统计表,采用myisam,按期作统计.通常的对统计的数据不会要求太精准的状况下适用。
2.尽可能不要在数据库中作运算。
3.避免负向查询和%前缀模糊查询。
4.不在索引列作运算或者使用函数。
5.不要在生产环境程序中使用select * from 的形式查询数据。只查询须要使用的列。
6.查询尽量使用limit减小返回的行数,减小数据传输时间和带宽浪费。
7.where子句尽量对查询列使用函数,由于对查询列使用函数用不到索引。
8.避免隐式类型转换,例如字符型必定要用’’,数字型必定不要使用’’。
9.全部的SQL关键词用大写,养成良好的习惯,避免SQL语句重复编译形成系统资源的浪费。
10.联表查询的时候,记得把小结果集放在前面,遵循小结果集驱动大结果集的原则。
11.开启慢查询,按期用explain优化慢查询中的SQL语句。
1、备份的目的
作灾难恢复:对损坏的数据进行恢复和还原
需求改变:因需求改变而须要把数据还原到改变之前
测试:测试新功能是否可用
2、备份须要考虑的问题
能够容忍丢失多长时间的数据;
恢复数据要在多长时间内完;
恢复的时候是否须要持续提供服务;
恢复的对象,是整个库,多个表,仍是单个库,单个表。
3、备份的类型
一、根据是否须要数据库离线
冷备(cold backup):须要关mysql服务,读写请求均不容许状态下进行;
温备(warm backup): 服务在线,但仅支持读请求,不容许写请求;
热备(hot backup):备份的同时,业务不受影响。
注:
一、这种类型的备份,取决于业务的需求,而不是备份工具
二、MyISAM不支持热备,InnoDB支持热备,可是须要专门的工具
二、根据要备份的数据集合的范围
彻底备份:full backup,备份所有字符集。
增量备份: incremental backup 上次彻底备份或增量备份以来改变了的数据,不能单独使用,要借助彻底备份,备份的频率取决于数据的更新频率。
差别备份:differential backup 上次彻底备份以来改变了的数据。
建议的恢复策略:
彻底+增量+二进制日志
彻底+差别+二进制日志
三、根据备份数据或文件
物理备份:直接备份数据文件
优势:备份和恢复操做都比较简单,可以跨mysql的版本,恢复速度快,属于文件系统级别的
建议:不要假设备份必定可用,要测试mysql>check tables;检测表是否可用
逻辑备份: 备份表中的数据和代码
优势:恢复简单、备份的结果为ASCII文件,能够编辑与存储引擎无关能够经过网络备份和恢复
缺点:备份或恢复都须要mysql服务器进程参与备份结果占据更多的空间,浮点数可能会丢失精度 还原以后,缩影须要重建
四:备份的对象
一、 数据;
二、配置文件;
三、代码:存储过程、存储函数、触发器
四、os相关的配置文件
五、复制相关的配置
六、二进制日志
5、备份和恢复的实现
一、利用select into outfile实现数据的备份与还原。
二、利用mysqldump工具对数据进行备份和还原
三、利用lvm快照实现几乎热备的数据备份与恢复
四、基于Xtrabackup作备份恢复。
优点:
一、快速可靠的进行彻底备份
二、在备份的过程当中不会影响到事务
三、支持数据流、网络传输、压缩,因此它能够有效的节约磁盘资源和网络带宽。
四、能够自动备份校验数据的可用性。
1、建立用户:
CREATE USER用于建立新的MySQL帐户。要使用CREATE USER,您必须拥有mysql数据库的全局CREATE USER权限,或拥有INSERT权限。对于每一个帐户,CREATE USER会在没有权限的mysql.user表中建立一个新记录。若是帐户已经存在,则出现错误。
使用自选的IDENTIFIED BY子句,能够为帐户给定一个密码。user值和 密码的给定方法和GRANT语句一 样。特别是,要在纯文本中指定密码,需忽略PASSWORD关键词。要把 密码指定为由PASSWORD()函数返回的混编值,需包含关键字PASSWORD
The create user command:mysql> CREATE USER yy IDENTIFIED BY ‘123’;
面创建的用户能够在任何地方登录。
mysql> CREATE USER yy@localhost IDENTIFIED BY ‘123’;
2、受权:
命令:GRANT privileges ON databasename.tablename TO ‘username’@’host’
说明: privileges - 用户的操做权限,如SELECT , INSERT , UPDATE 等.若是要授予所的权限则使
用 ALL.;databasename - 数据库名,tablename-表名,若是要授予该用户对全部数据库和表的相应操
做权限则可用表示, 如.*.
GRANT SELECT, INSERT ON test.user TO ‘pig’@’%’;
GRANT ALL ON . TO ‘pig’@’%’;
注意:用以上命令受权的用户不能给其它用户受权,若是想让该用户能够受权,用如下命令:
GRANT privileges ON databasename.tablename TO ‘username’@’host’ WITH GRANT OPTION;
刷新系统权限表
flush privileges;
3、设置与更改用户密码
命令:SET PASSWORD FOR ‘username’@’host’ = PASSWORD(‘newpassword’);若是是当前登录用户用SET PASSWORD = PASSWORD(“newpassword”);
例子:SET PASSWORD FOR ‘pig’@’%’ = PASSWORD(“123456”);
或:update mysql.user set password=password(‘新密码’) where User=”phplamp” and Host=”localhost”;
4、撤销用户权限
命令: REVOKE privilege ON databasename.tablename FROM ‘username’@’host’;
说明: privilege, databasename, tablename - 同受权部分.
例子: REVOKE SELECT ON . FROM ‘pig’@’%’;
注意: 假如你在给用户’pig’@’%’受权的时候是这样的(或相似的):GRANT SELECT ON test.user TO ‘pig’@’%’, 则在使用 REVOKE SELECT ON . FROM ‘pig’@’%’;命令并不能撤销该用户对test数据库中user表的SELECT 操做.相反,若是受权使用的是GRANT SELECT ON . TO ‘pig’@’%’;则REVOKE SELECT ON test.user FROM ‘pig’@’%’;命令也不能撤销该用户对test数据库中user表的Select 权限.具体信息能够用命令SHOW GRANTS FOR ‘pig’@’%’; 查看.
5、删除用户
命令: DROP USER ‘username’@’host’;
或:DELETE FROM user WHERE User=”phplamp” and Host=”localhost”;
//删除用户的数据库
mysql>drop database phplampDB;
一、安装配置,两台服务器,分别安装好MySQL。采用单向同步的方式,就是Master的数据是主的数据,而后slave主动去Master哪儿同步数据回来。两台服务器的配置同样,把关键的配置文件拷贝一下,两台服务器作相同的拷贝配置文件操做。
二、配置Master服务器,要考虑咱们须要同步那个数据库,使用那个用户同步,咱们这里为了简单起见,就使用root用户进行同步,而且只须要同步数据库abc。
三、配置Slave服务器,咱们的slave服务器主要是主动去Master服务器同步数据回来。
四、测试安装,首先查看一下slave的主机日志:检查是否链接正常, 在Master查看信息,查看Master状态:查看Master下MySQL进程信息:在slave上查看信息:查看slave状态:查看slave下MySQL进程信息:再在Master的abc库里创建表结构而且插入数据,而后检查slave有没有同步这些数据,就可以检查出是否设置成功。
查看MYSQL数据库中全部用户
SELECT DISTINCT CONCAT(‘User: ”’,user,”’@”’,host,”’;’) AS query FROM mysql.user;
查看数据库中具体某个用户的权限
show grants for ‘cactiuser’@’%’;
多数状况下,能够认为若是一个资源被锁定,它总会在之后某个时间被释放。而死锁发生在当多个进程访问同一数据库时,其中每一个进程拥有的锁都是其余进程所需的,由此形成每一个进程都没法继续下去。简单的说,进程A等待进程B释放他的资源,B又等待A释放他的资源,这样就互相等待就造成死锁。
虽然进程在运行过程当中,可能发生死锁,但死锁的发生也必须具有必定的条件,死锁的发生必须具有如下四个必要条件。
1)互斥条件:指进程对所分配到的资源进行排它性使用,即在一段时间内某资源只由一个进程占用。若是此时还有其它进程请求资源,则请求者只能等待,直至占有资源的进程用毕释放。
2)请求和保持条件:指进程已经保持至少一个资源,但又提出了新的资源请求,而该资源已被其它进程占有,此时请求进程阻塞,但又对本身已得到的其它资源保持不放。
3)不剥夺条件:指进程已得到的资源,在未使用完以前,不能被剥夺,只能在使用完时由本身释放。
4)环路等待条件:指在发生死锁时,必然存在一个进程——资源的环形链,即进程集合{P0,P1,P2,•••,Pn}中的P0正在等待一个P1占用的资源;P1正在等待P2占用的资源,……,Pn正在等待已被P0占用的资源。
下列方法有助于最大限度地下降死锁:
(1)按同一顺序访问对象。
(2)避免事务中的用户交互。
(3)保持事务简短并在一个批处理中。
(4)使用低隔离级别。
(5)使用绑定链接。
实现数据库安全性控制的经常使用方法和技术有:用户标识和鉴别;存取控制;视图机制;审计;数据加密;
Union由于要进行重复值扫描,因此效率低。若是合并无刻意要删除重复行,那么就使用Union All两个要联合的SQL语句 字段个数必须同样,并且字段类型要“相容”(一致);
union和union all的区别是,union会自动压缩多个结果集合中的重复结果,而union all则将全部的结果所有显示出来,无论是否是重复。
Union:对两个结果集进行并集操做,不包括重复行,同时进行默认规则的排序;
Union All:对两个结果集进行并集操做,包括重复行,不进行排序;
Intersect:对两个结果集进行交集操做,不包括重复行,同时进行默认规则的排序;
Minus:对两个结果集进行差操做,不包括重复行,同时进行默认规则的排序。
能够在最后一个结果集中指定Order by子句改变排序方式。
mysqldump -hhostname -uusername -ppassword databasename > backupfile.sql
备份MySQL数据库为带删除表的格式
备份MySQL数据库为带删除表的格式,可以让该备份覆盖已有数据库而不须要手动删除原有数据库。
mysqldump -–add-drop-table -uusername -ppassword databasename > backupfile.sql
直接将MySQL数据库压缩备份
mysqldump -hhostname -uusername -ppassword databasename | gzip > backupfile.sql.gz
备份MySQL数据库某个(些)表
mysqldump -hhostname -uusername -ppassword databasename specific_table1 specific_table2 > backupfile.sql
同时备份多个MySQL数据库
mysqldump -hhostname -uusername -ppassword –databases databasename1 databasename2 databasename3 > multibackupfile.sql
仅仅备份数据库结构
mysqldump –no-data –databases databasename1 databasename2 databasename3 > structurebackupfile.sql
备份服务器上全部数据库
mysqldump –all-databases > allbackupfile.sql
还原MySQL数据库的命令
mysql -hhostname -uusername -ppassword databasename < backupfile.sql
还原压缩的MySQL数据库
gunzip < backupfile.sql.gz | mysql -uusername -ppassword databasename
将数据库转移到新服务器
mysqldump -uusername -ppassword databasename | mysql –host=... -C databasename
第一步 检查系统的状态
经过操做系统的一些工具检查系统的状态,好比CPU、内存、交换、磁盘的利用率,根据经验或与系统正常时的状态相比对,有时系统表面上看起来看空闲,这也可能不是一个正常的状态,由于cpu可能正等待IO的完成。除此以外,还应观注那些占用系统资源(cpu、内存)的进程。
1.1 使用sar来检查操做系统是否存在IO问题
1.2 使用vmstat监控内存 cpu资源
1.3 磁盘IO问题,处理方式:作raid10提升性能
1.4 网络问题,telnet一下MySQL对外开放的端口,若是不通的话,看看防火墙是否正确设置了。另外,看看MySQL是否是开启了skip-networking的选项,若是开启请关闭。
第二步 检查mysql参数
2.1 max_connect_errors
2.2 connect_timeout
2.3 skip-name-resolve
2.4 slave-net-timeout=seconds
2.5 master-connect-retry
第三步 检查mysql 相关状态值
3.1 关注链接数
3.2 关注下系统锁状况
3.3 关注慢查询(slow query)日志
1.导出整个数据库
mysqldump -u用户名 -p密码 数据库名 > 导出的文件名
C:\Users\jack> mysqldump -uroot -pmysql sva_rec > e:\sva_rec.sql
2.导出一个表,包括表结构和数据
mysqldump -u用户名 -p 密码 数据库名 表名> 导出的文件名
C:\Users\jack> mysqldump -uroot -pmysql sva_rec date_rec_drv> e:\date_rec_drv.sql
3.导出一个数据库结构
C:\Users\jack> mysqldump -uroot -pmysql -d sva_rec > e:\sva_rec.sql
4.导出一个表,只有表结构
mysqldump -u用户名 -p 密码 -d数据库名 表名> 导出的文件名
C:\Users\jack> mysqldump -uroot -pmysql -d sva_rec date_rec_drv> e:\date_rec_drv.sql
5.导入数据库
经常使用source 命令
进入mysql数据库控制台,
如mysql -u root -p
mysql>use 数据库
而后使用source命令,后面参数为脚本文件(如这里用到的.sql)
mysql>source d:wcnc_db.sql
输入show processlist;
若是有SUPER权限,则能够看到所有的线程,不然,只能看到本身发起的线程(这是指,当前对应的MySQL账户运行的线程)。
1、MySQL 链接本地数据库,用户名为“root”,密码“123”(注意:“-p”和“123” 之间不能有空格)
C:>mysql -h localhost -u root -p123
2、MySQL 链接远程数据库(192.168.0.201),端口“3306”,用户名为“root”,密码“123”
C:>mysql -h 192.168.0.201 -P 3306 -u root -p123
MySQL 复制基于主服务器在二进制日志中跟踪全部对数据库的更改(更新、删除等等)。每一个从服务器从主服务器接收主服务器已经记录到其二进制日志的保存的更新,以便从服务器能够对其数据拷贝执行相同的更新。
一、彻底备份,这是大多数人经常使用的方式,它能够备份整个数据库,包含用户表、系统表、索引、视图和存储过程等全部数据库对象。但它须要花费更多的时间和空间,因此,通常推荐一周作一次彻底备份。
二、事务日志备份,事务日志是一个单独的文件,它记录数据库的改变,备份的时候只须要复制自上次备份以来对数据库所作的改变,因此只须要不多的时间。为了使数据库具备鲁棒性,推荐每小时甚至更频繁的备份事务日志。
三、差别备份也叫增量备份。它是只备份数据库一部分的另外一种方法,它不使用事务日志,相反,它使用整个数据库的一种新映象。它比最初的彻底备份小,由于它只包含自上次彻底备份以来所改变的数据库。它的优势是存储和恢复速度快。推荐天天作一次差别备份。
四、文件备份,数据库能够由硬盘上的许多文件构成。若是这个数据库很是大,而且一个晚上也不能将它备份完,那么能够使用文件备份每晚备份数据库的一部分。因为通常状况下数据库不会大到必须使用多个文件存储,因此这种备份不是很经常使用。
查看mysql的存储引擎:show plugins;
如何在mysql某个表中随机抽取10条记录
1.经过MYSQL内置的函数来操做,具体SQL代码以下:
SELECT * FROM tablename ORDER BY RAND() LIMIT 10
2.不要将大量的工做给数据库去作,这样会致使数据库在某一集中并发时间内锁死并阻塞。建议经过PHP随机生成一下1-X(总行数)之间的数字,而后将这10个随机数字做为查询条件,具体语句如:
SELECT * FROM tablename where ID in (2,8,4,11,12,9,3,1,33)
可能你还要进行重复排除,而且须要在程序中将10个值串联并链接进入SQL语句中。
show full processlist,在user字段中查看有哪些用户
方法一: (适用于管理员或者有全局权限的用户重设其它用户的密码)
进入命令行模式
mysql -u root -p
mysql>use mysql;
mysql> UPDATE user SET password=PASSWORD(“new password”) WHERE user=’username’;
mysql> FLUSH PRIVILEGES;
mysql> quit;
方法二:
mysql -u root -p
mysql>use mysql;
mysql> SET PASSWORD FOR username=PASSWORD(‘new password’);
mysql> QUIT
方法三:
mysqladmin -u root “old password” “new password”
注:new password请输入你想要设置的密码。
有两种方法,一种方法使用mysql的check table和repair table 的sql语句,另外一种方法是使用MySQL提供的多个myisamchk, isamchk数据检测恢复工具。
1.数据库的设计:尽可能把数据库设计的更小的占磁盘空间.
1) 尽量使用更小的整数类型.(mediumint就比int更合适).
2) 尽量的定义字段为not null,除非这个字段须要null.
3) 若是没有用到变长字段的话好比varchar,那就采用固定大小的纪录格式好比char.
4) 表的主索引应该尽量的短.这样的话每条纪录都有名字标志且更高效.
5) 只建立确实须要的索引。索引有利于检索记录,可是不利于快速保存记录。若是老是要在表的组合字段上作搜索,那么就在这些字段上建立索引。索引的第一部分必须是最常使用的字段.若是老是须要用到不少字段,首先就应该多复制这些字段,使索引更好的压缩。
6) 全部数据都得在保存到数据库前进行处理。
7) 全部字段都得有默认值。
8) 在某些状况下,把一个频繁扫描的表分红两个速度会快好多。在对动态格式表扫描以取得相关记录时,它可能使用更小的静态格式表的状况下更是如此。
2.系统的用途
1) 尽可能使用长链接.
2) explain复杂的SQL语句。
3) 若是两个关联表要作比较话,作比较的字段必须类型和长度都一致.
4) LIMIT语句尽可能要跟order by或者 distinct.这样能够避免作一次full table scan.
5) 若是想要清空表的全部纪录,建议用truncate table tablename而不是delete from tablename.
6) 能使用STORE PROCEDURE 或者 USER FUNCTION的时候.
7) 在一条insert语句中采用多重纪录插入格式.并且使用load data infile来导入大量数据,这比单纯的insert快好多.
8) 常常OPTIMIZE TABLE 来整理碎片.
9) 还有就是date 类型的数据若是频繁要作比较的话尽可能保存在unsigned int 类型比较快。
3.系统的瓶颈
1) 磁盘搜索。并行搜索,把数据分开存放到多个磁盘中,这样能加快搜索时间.
2) 磁盘读写(IO)。能够从多个媒介中并行的读取数据。
3) CPU周期。数据存放在主内存中.这样就得增长CPU的个数来处理这些数据。
4) 内存带宽。当CPU要将更多的数据存放到CPU的缓存中来的话,内存的带宽就成了瓶颈.
mysql> show engines; 显示了可用的数据库引擎的所有名单以及在当前的数据库服务器中是否支持这些引擎。
VARCHAR和CHAR类型,varchar是变长的,须要额外的1-2个字节存储,能节约空间,可能会对性能有帮助。但因为是变长,可能发生碎片,如更新数据;
使用ENUM代替字符串类型,数据实际存储为整型。
字符串类型
要尽量地避免使用字符串来作标识符,由于它们占用了不少空间而且一般比整数类型要慢。特别注意不要在MYISAM表上使用字符串标识符。MYISAM默认状况下为字符串使用了压缩索引(Packed Index),这使查找更为缓慢。据测试,使用了压缩索引的MYISAM表性能要慢6倍。
还要特别注意彻底‘随机’的字符串,例如由MD5()、SHA1()、UUID()产生的。它们产生的每个新值都会被任意地保存在很大的空间范围内,这会减慢INSERT及一些SELECT查询。
1)它们会减慢INSERT查询,由于插入的值会被随机地放入索引中。这会致使分页、随机磁盘访问及汇集存储引擎上的汇集索引碎片。
2)它们会减慢SELECT查询,由于逻辑上相邻的行会分布在磁盘和内存中的各个地方。
3)随机值致使缓存对全部类型的查询性能都不好,由于它们会使缓存赖以工做的访问局部性失效。若是整个数据集都变得一样“热”的时候,那么把特定部分的数据缓存到内存中就没有任何的优点了。而且若是工做集不能被装入内存中,缓存就会进行不少刷写的工做,而且会致使不少缓存未命中。
若是保存UUID值,就应该移除其中的短横线,更好的办法是使用UHEX()把UUID值转化为16字节的数字,并把它保存在BINARY(16)列中。
330六、1521
(1)有多少种日志 错误日志:记录出错信息,也记录一些警告信息或者正确的信息 慢查询日志:设置一个阈值,将运行时间超过该值的全部SQL语句都记录到慢查询的日志文件中。 二进制日志:记录对数据库执行更改的全部操做 查询日志:记录全部对数据库请求的信息,不论这些请求是否获得了正确的执行。 (2)日志的存放形式 (3)事务是如何经过日志来实现的,说得越深刻越好。 在Innodb存储引擎中,事务日志是经过redo和innodb的存储引擎日志缓冲(Innodb log buffer)来实现 的,当开始一个事务的时候,会记录该事务的lsn(log sequence number)号; 当事务执行时,会往InnoDB存 储引擎的日志的日志缓存里面插入事务日志;当事务提交时,必须将存储引擎的日志缓冲写入磁盘(经过 innodb_flush_log_at_trx_commit来控制),也就是写数据前,须要先写日志。这种方式称为“预写日志方 式”, innodb经过此方式来保证事务的完整性。也就意味着磁盘上存储的数据页和内存缓冲池上面的页是不一样步 的,是先写入redo log,而后写入data file,所以是一种异步的方式。 隔离性: 经过锁实现 原子性、一致性和持久性是经过redo和undo来完成的。