mysql必知必会读书笔记

本文是mysql必知必会读书笔记,主要记录书中介绍的sql语句需要注意的点。具体的sql语法及格式可参见: 点击打开链接
检索:
select 得到的结果是未排序的 除非明确指明排序规则
使用通配符* 检索数据时,可以检索到未命名的列,但是检索效率较低,应尽量在检索时指定列名。
distinct 作用于所有检索列,而不是部分列。
检索出来的行索引从0开始而不是1。
完全限定名是为了联合查询时解决当两个表有相同列名时列名的二义性

排序:
可以按非检索字段进行排序。
多字段排序:select * from table order by A desc,B,C desc;

通配符效率低尽量不用,用其他语句替代
% 匹配任意字符任意次数 _ 匹配任意字符一次

正则表达式:
mysql只实现了部分正则表达式。
regexp ‘1000’ like ‘1000’ 将返回不同的值,因为regexp是部分匹配,而like是全部匹配。当前regexp可以使用定位符^ &完成全部匹配。

聚合函数:运行在多个行,返回单个值。聚合函数以列名做参数(coun可以使用*做参数)
除了count 其他只能运行在单列上。

分组:但个聚合函数,是将这个查询出来的数据进行处理,没办法针对每个部分数据进行处理。而分组将数据分为多个逻辑组,对每个组进行处理(聚合函数直接作用在每个组)。
having 和 where 用法相同,having 在group by 之后是过滤分组(一次过滤多行),而 where 是过滤行(一次过滤单行)。也可以里理解为 where 是分组前进行过滤,而having 是分组后进行过滤。
不要依赖与分组排序。

语句顺序:select from where group by order by limit

子查询:通常用于过滤和计算字段。
过滤 :select * from table where custid in (select custid from tableB)
计算字段:select custid,(select count(xxx) from tableB where cust = custid) from table 每检索出一行 都会执行一次子查询

外键:字段不是表的主键,是其他表的主键
外键约束:
cascade:主表中删除,副表的记录也删除
restrict:主表删除时 附表正在使用该外键,那么删除失败报错
set null:主表删除 副表中使用该外键的记录设置为null

联合:where inner join on 联合越多的表效率越差 (on 后边的条件 其实是限定 A表的行 对应 B表的哪个行 是限定行和行之间的对应关系)
其实就是多张表做笛卡尔积形成一张表,然后再用where进行过滤
自然联合:就是手动声明显示的列,去除了相同的列名
内部联合:只检索出两边都存在的行
外部连接:可以检索出某一侧不存在的行 left outer join right outer join

组合:union 联合是将多个表的列组合起来,组合是将多个查询结果的行组合起来。union 大部分情况下是 将where 的多个条件 拆分到多个查询中,只有union all 是where完成不了的(包含了重复行)
限制:多个查询必须有相同列、聚合函数、列的类型必须相同(或可以进行类型转换)
组合会自动去除重复的行,不想去除用 union all
如果在union 使用order by 则order by 必须放在最后一个查询后 。排序针对所有查询而不是最后一个查询

全文索引:索引相对于正则表达式和like效率更高。对结果进行了排序,匹配度较高的优先输出。
步骤:
索引程序从数据库中读取数据
索引程序对数据进行分词处理
索引程序根据分词建立索引文件
match(字段) agaist(“值”)
查询扩展:
两次搜索
第一次:找到匹配行,保存有用的词
第二次:利用第一次搜索的结果和所有的词进行匹配
可以按优先级匹配,过滤不匹配的行。

插入:
insert into table(l列名) values(值) values(值)
插入时,忽略的列,必须支持默认值。
insert 插入效率较低,频繁的插入可能会影响查询性能,可以一次插入多行,或者insert low_priority into 降低插入的优先级。
将从表中检索出的数据插入到另一张表:insert into table(l列名) select ......

更新:
update table set field = value where condition
如果没有条件,则更新所有行。ignore如果更新中出现错误,则整个操作被取消,恢复到更新前值。可通过set null 删除某 列值

删除:
delete from table where condition
删除所有行:更快的方法是使用truncate table,truncate 重新构造一个表删除原表,delete是逐行删除。


创建表:
create table tableName
{
fieldName type 是否允许null值
..........
primary_key(fieldName)
}
primary_key:指定主键 auto_increment:指定列值自增 default:默认值(不支持函数,只支持常量)
每个表最多只有一个auto_increment域,并且他必须被索引(如做主键)。
外键不能跨引擎。
删除表:drop table tableName
重命名表名:rename table OldtableName to NewtableName

更改表结构:
添加列: alter table tableName add fieldName
删除列: alter table tableName drop fieldName

视图:
语法: create view drop view 更新 = drop + create
视图是一张虚拟表,是一份动态数据,这份数据是用创建视图的检索语句检索出来的。所以当视图的源表数据发生更改时,视图的数据也同步发生改变,而改变视图的数据,也会对相应的源表进行修改。
视图的好处:重用检索语句 赋予用户某个表的部分列操作权限而不是整个表
特殊性:
(1)若创建视图时有order by ,则使用视图时order by会失效
(2)若创建视图时有where ,则使用视图时where 会和创建时的where 合并
当视图中存在 联合 子查询 分组 去重 等是不可以更新视图的数据的。

存储过程:类似于函数,将多条sql语句封装在一起,比分开执行sql效率更高。
语法:
调用:call proName(@paramer1,....)
创建:
create procedure proName( [out,in] paramerName type,.............) -- out in 分别代表传出 传入
begin

end;
删除:drop procedure

游标:针对查询出的结果集进行逐行操作,只能存在与存储过程和函数中。
语法:
定义:declare 游标名 cursor for 检索语句;
打开:open 游标名
关闭:close 游标名 -- 超出作用域会自动关闭
使用: fetch   next from mycursor into id,pname,pprice,pdescription;

触发器:类似于事件通知
语法:
创建:
CREATE TRIGGER trigger_nametrigger_time -- trigger_time [ BEFORE 或 AFTER]
trigger_event ON tbl_name         -- trigger_event [ INSERT、UPDATE、DELETE]
FOR EACH ROWtrigger_stmt -- 一个查询语句或者 begin end的多条语句
删除: DROP TRIGGER

old new 解释:old就是表中已有的数据 new就是更改时用户传进去的数据
Insert:new是插入的数据
Update:new是更新数据 old是被更新的数据
Delete:old 是删除的数据


若SQL语句或触发器执行失败,MySQL 会回滚事务,有:
①如果 BEFORE 触发器执行失败,SQL 无法正确执行。
②SQL 执行失败时,AFTER 型触发器不会触发。
③AFTER 类型的触发器执行失败,SQL 会回滚。

详细语法参见:点击打开链接


你可能感兴趣的:(mysql)