MYSQL基础语法二

1、数据类型

1.1、数值型

MySQL支持多种数值型数据类型,包括整数型、小数型和布尔型。

1.1.1、整数型

MySQL支持多种整数型数据类型,包括TINYINT、SMALLINT、MEDIUMINT、INT和BIGINT。

  • TINYINT:1字节,取值范围为-128到127或0到255。
  • SMALLINT:2字节,取值范围为-32768到32767或0到65535。
  • MEDIUMINT:3字节,取值范围为-8388608到8388607或0到16777215。
  • INT:4字节,取值范围为-2147483648到2147483647或0到4294967295。
  • BIGINT:8字节,取值范围为-9223372036854775808到9223372036854775807或0到18446744073709551615。

1.1.2、小数型

MySQL支持多种小数型数据类型,包括FLOAT、DOUBLE和DECIMAL。

  • FLOAT:4字节,单精度浮点数,精度为7位。
  • DOUBLE:8字节,双精度浮点数,精度为15位。
  • DECIMAL:可变长度,用于存储精确的小数,精度和数据长度可以自定义。

1.1.3、布尔型

MySQL支持布尔型数据类型,即BOOLEAN或BOOL。它只占用1位,取值为TRUE或FALSE。

1.2、日期型

MySQL支持多种日期型数据类型,包括DATE、TIME、DATETIME、TIMESTAMP和YEAR。

  • DATE:用于存储日期,格式为YYYY-MM-DD。
  • TIME:用于存储时间,格式为HH:MM:SS。
  • DATETIME:用于存储日期时间,格式为YYYY-MM-DD HH:MM:SS。
  • TIMESTAMP:用于存储时间戳,格式为YYYY-MM-DD HH:MM:SS。
  • YEAR:用于存储年份,格式为YYYY。

1.3、字符串型

MySQL支持多种字符串型数据类型,包括CHAR、VARCHAR、TEXT、BLOB和ENUM。

1.3.1、CHAR和VARCHAR

CHAR和VARCHAR都用于存储字符串,但它们的存储方式不同。CHAR是一种固定长度的字符串类型,VARCHAR是一种可变长度的字符串类型。

  • CHAR:用于存储固定长度的字符串,长度为0到255个字符。
  • VARCHAR:用于存储可变长度的字符串,长度为0到65535个字符。

1.3.2、TEXT和BLOB

TEXT和BLOB用于存储大量的文本或二进制数据。

  • TEXT:用于存储大量的文本数据,最大长度为65535个字符。
  • BLOB:用于存储大量的二进制数据,最大长度为65535个字节。

1.3.3、ENUM

  • ENUM用于存储枚举类型的数据,如性别、状态等。

1.4、二进制型

MySQL支持多种二进制型数据类型,包括BIT、BINARY和VARBINARY。

  • BIT:用于存储比特位,长度为1到64个比特位。
  • BINARY:用于存储固定长度的二进制数据,长度为0到255个字节。
  • VARBINARY:用于存储可变长度的二进制数据,长度为0到65535个字节。

五、其他类型

MySQL还支持多种其他类型的数据,包括SET、JSON和Geometry。

  • SET:用于存储一组可选值,最多可以有64个选项。
  • JSON:用于存储JSON格式的数据。
  • Geometry:用于存储几何类型的数据,如点、线、面等。

2、常用语法

MySQL常用列属性有:null、not null、default、primary key、auto_increment、comment。

2.1、空属性: null和not null

sql 复制代码
/*空属性: null和not null*/
空属性: null(空,默认) 和 not null(不为空). mysql数据库默认字段都是为null的,实际开发过程中尽可能保证所有的数据都不应该为null,空数据没有意义.
例如: create table test(
    a int not null,
    b int
);
insert into test (a,b) values(10,null);
insert into test (a,b) values(null,10);--报错

2.2、默认值:default

sql 复制代码
/*默认值: default*/
default: 自定义默认值属性,通常配合not null一起使用.
例如: create table test1(
    a int not null default 200,
    b int
);
insert into test1(b) values(20);--或 insert into test1(a,b) values(default,20);

2.3、主键:primary key

sql 复制代码
/*主键|唯一索引*/
Mysql中提供了多种索引? (下文索引更多解析)
1.主键索引:primary key
2.唯一索引:unique key
3.全文索引:fulltext index
4.普通索引:key 或 index

主键:primary key  一张表中只能有一个字段可以使用对应的主键,用来唯一的约束该字段里面的数据,不能重复和不能为null.
设置主键有两种方式:
(1)在定义一个字段的时候直接在后面进行设置primary key
例如: create table test2(
  id int(10) unsigned not null primary key,
  name char(20) not null default ''
);
(2)定义完字段后再定义主键
例如: create table test3(
  id int(10) unsigned not null,
  name char(20) not null default '',
  primary key (id)
);
唯一键:unique key 解决表中多个字段需要唯一性约束的问题.
例如:create table test4(
  id int(10) unsigned not null,
  name char(20) not null default '',
  goods varchar(100) not null default '',
  primary key (id),
  unique key (name,goods)
);

2.4、自增长:auto_increment

sql 复制代码
/*自动增长: auto_increment*/
自增长属性:每次插入记录的时候,自动的为某个字段的值加1(基于上一个记录). 通常跟主键搭配.
自增长规则:(1)任何一个字段要做自增长前提必须是一个索引  (2)自增长字段必须是整型数字
例如: create table test5(
  id int(10) unsigned not null auto_increment,
  name char(20) not null default '',
  primary key (id)
);

2.5、列描述:comment

sql 复制代码
/*列描述 comment*/
列描述(注释):comment 与其他的注释符不同之处在于,这里的注释内容属于列定义的一部分.
例如:create table user(
  id int(10) unsigned not null auto_increment comment 'id',
  name char(20) not null default '' comment '名字',
  primary key (id)
)engine=InnoDB default charset=utf8 comment='用户表';

2.6、索引

sql 复制代码
#索引
/*索引的概述和优缺点和种类*/
什么是索引?
索引是一种特殊的文件(InnoDB数据表上的索引是表空间的一个组成部分),它们包含着对数据表里所有记录的引用指针.
类比理解:数据库中的索引相当于书籍目录一样,能加快数据库的查询速度.
没有索引的情况,数据库会遍历全部数据后选择符合条件的选项.
创建相应的索引,数据库会直接在索引中查找符合条件的选项.

索引的性质分类:
索引分为聚集索引和非聚集索引两种,聚集索引是索引中键值的逻辑顺序决定了表中相应行的物理顺序,而非聚集索引是不一样;
聚集索引能提高多行检索的速度,而非聚集索引对于单行的检索很快.

索引的优点:
(1)加快数据检索速度 (创建索引主要原因)
(2)创建唯一性索引,保证数据库表中每一行数据的唯一性
(3)加速表和表之间的连接
(4)使用分组和排序子句对数据检索时,减少检索时间
(5)使用索引在查询的过程中,使用优化隐藏器,提高系统的性能

索引的缺点:
(1)创建索引和维护索引要耗费时间,时间随着数据量的增加而增加
(2)索引需要占用物理空间和数据空间
(3)表中的数据操作插入、删除、修改, 维护数据速度下降

索引种类
(1)普通索引: 仅加速查询
(2)唯一索引: 加速查询 + 列值唯一(可以有null)
(3)主键索引: 加速查询 + 列值唯一(不可以有null)+ 表中只有一个
(4)组合索引: 多列值组成一个索引,专门用于组合搜索,其效率大于索引合并
(5)全文索引: 对文本的内容进行分词,进行搜索 (注意:目前仅有MyISAM引擎支持)

/*创建表时直接指定索引*/
--创建主键索引
例如:create table student(
  id int(10) unsigned not null auto_increment comment 'id主键索引',
  name char(20) not null default '' comment '名字',
  class varchar(50) not null default '' comment '班级',
  seat_number smallint(5) not null default 0 comment '座位编号',
  primary key (id)
)engine=InnoDB default charset=utf8 comment='学生表';
/*创建索引*/
create [unique唯一索引][clustered聚集索引] index <索引名>
on <表名>(<列名称>[<排序>],<列名称>[<排序>]...);

语法解析:其中unique和clustered为可选项. 注意:基本表上最多仅仅能建立一个聚集索引.
"列名称":规定需要索引的列. "排序":可选asc(升序)和desc(降序)缺省值为asc.
--创建唯一索引(unique key 简写 unique)
例如:create unique index number on student(seat_number desc);
--创建普通索引
例如:create index name_class on student(name asc,class desc);
/*删除索引*/
drop index <索引名> on 表名;
例如:drop index number on student;

2.7、外键

sql 复制代码
/*外键约束: foreign key */
外键约束: foreign key 被约束的表叫做副表,外键设置在副表上面,外键引用主键字段所在的表叫做主表. (作用:约束两张表的数据)
外键定义语法: constraint 外键约束名称 foreign key(外键字段) references 主表名称(引用字段)
外键数据操作:
1.当有外键约束之后,添加数据的时候,先添加主表数据,再添加副表数据
2.当有了外键约束,修改数据的时候,先改副表的数据,在修改主表的数据
3.当有了外键约束,删除数据的时候,也是先删除副表的数据,再删除主表的数据
外键注意事项:
1.外键约束只有InnoDB存储引擎才支持.
2.实际项目中往往会用到外键的设计思想,但往往不会真正的从语法上进行外键约束. 因为外键约束的级联操作可能会带来一些现实的逻辑问题. 另外使用外键会较低mysql的效率.

2.8、储存引擎

sql 复制代码
/*储存引擎: engine*/
常见的引擎:Myisam InnoDB BDB Memory Archive 等

不同的引擎在保存表的结构和数据时采用不同的方式?
MyISAM表文件含义:.frm表定义,.MYD表数据,.MYI表索引
InnoDB表文件含义:.frm表定义,表数据空间文件(存放表的数据和索引)和日志文件

2.9、innodb与myisam的区别

sql 复制代码
MySQL中innodb与myisam的区别
(1):InnoDB支持事物,MyISAM不支持事物
(2):InnoDB支持行级锁,MyISAM支持表级锁
(3):InnoDB支持快照数据(MVCC),MyISAM不支持
(4):InnoDB支持外键,MyISAM不支持
(5):InnoDB不支持全文索引,MyISAM支持

innodb使用的是行级锁:只有在增删改查时匹配的条件字段带有索引时,innodb才会使用行级锁.(行级锁:要为匹配条件字段加索引)
innodb使用的是表级锁:如果增删改查时匹配的条件字段不带有索引时,innodb使用的将是表级锁.(表级锁:数据库全表查询,需要将整张表加锁,保证查询匹配的正确性)
触发读锁:就是用select命令时触发读锁.
触发写锁:就是在你使用update,delete,insert时触发写锁,并且使用rollback或commit后解除本次锁定
更好的区分:读写锁和表级锁行级锁. 将读写锁叫做权限锁(决定了加锁后用户有哪些操作权限),将表级锁行级锁叫做对象锁(决定将锁加在某一行还是整张表)

MVCC多版本并发控制,也可称之为一致性非锁定读;它通过行的多版本控制方式来读取当前执行时间数据库中的行数据. 实质上使用的是快照数据.
为什么要使用MVCC?
消除锁的开销. (如果要保证数据的一致性,最简单的方式就是对操作数据进行加锁,但是加锁不可避免的会有锁开销. 所以使用MVCC能避免进行加锁的方式并提高并发.)

2.10、运算符和逻辑运算符

sql 复制代码
--比较运算符(常用示例) <, >, <=, >=, =, !=或<>, IS NULL
    between and | not between and --例如: between A and B; 相当于区间[A,B]; 
    in | not in --例如:in表示某个值出现; 
    not in表示没出现在一个集合之中; 
    is null | is not null --空值查询; 
    like --通配符;  
    _  代表任意的单个字符; 
    %  代表任意的字符;
--逻辑运算符
    &&(AND), ||(OR), !(NOT), XOR异或

2.11、group by

sql 复制代码
--group by子句 (分组)
  --group by 字段/别名 [排序方式]    分组后排序: asc 升序(默认),desc 降序
  --统计函数需配合group by使用:
  count 返回不同的非NULL统计值  count(*)、count(字段)
  sum 求和; max 求最大值; min 求最小值; avg 求平均值
select class, sum(score) as sum 
from student 
group by class desc;--查询各个班级总成绩,分组班级降序.

select id,class, max(score) as max 
from student where score>80  
group by class;--查询各个班级最高成绩,分数要大于80,分组班级升序.

2.12、having

sql 复制代码
--having 子句 (条件查询)
 --where功能、用法相同,执行时机不同.
 --本质区别:where子句是把磁盘上的数据筛选到内存上,而having子句是把内存中的数据再次进行筛选.
 --where不可以使用统计函数. 一般需用统计函数配合group by才会用到having
例如:
select class, min(score) as min 
from student 
where min(score)>80 
group by class;--报错

select class, min(score) as min 
from student 
group by class 
having min(score)>80;--查询各个班级最低成绩,分组班级,最低分数大于80

2.13、order by

sql 复制代码
--order by子句  (排序)
  --order by 字段1[asc|desc],字段n[asc|desc]
  --排序: asc 升序(默认),desc 降序
例如:
select * from 
student 
where score > 80 
order by score,name desc;--查询score大于80,排序score升序和name降序

2.14、联合查询

sql 复制代码
/*联合查询 关键字:union*/ 
--联合查询:就是将多个查询结果进行纵向上的拼接. (select语句2的查询结果放在select语句1查询结果的后面)
--语法:
  select语句1
  union [all | distinct]
  select 语句2
  union [all | distinct]
  select 语句n

例如:查询A班级最高成绩和B班级最低成绩? 
(select name, class,score from student where class='A' order by score desc limit 1)
union
(select name, class,score from student where class='B' order by score limit 1);

2.15、连接查询

sql 复制代码
/*连接查询*/
 将多个表的字段进行连接,可以指定连接条件.
--交叉连接 cross join
select  *|字段列表 from 表名1 cross join 表名2;

一张表的一条记录去连接另一张表中的所有记录,并且保存所有的记录包含两个表的所有的字段.
结果上看,就是对两张表做笛卡尔积,有n1*n2条记录.
例如:select * from student cross join score;

2.16、内连接

sql 复制代码
--内连接 inner join
select *|字段列表 from 左表 [inner] join 右表 on 左表.字段 = 右表.字段 [五子句];

数据在左表中存在,同时在右表中又有对应的匹配的结果才会被保存. 如果没有匹配上,数据没有意义不会保存.
通常就是两张表中存在相同的某个字段.(项目中通常是关联主键ID) using() 用法连接两表公共字段. 例如:using(ID)
select student.*, teacher.class as t_class, teacher.name as t_name 
from student join teacher on student.class = teacher.class;

2.17、左外连接

sql 复制代码
-- 左外连接 left join
  select *|字段列表 from 左表 left [outer] join 右表 on 左表.字段 = 右表.字段 [五子句];
  如果数据不存在,左表记录会出现,而右表为null填充
例如:
select student.*, teacher.class as t_class, teacher.name as t_name 
from student left join teacher on student.class = teacher.class;

2.18、右连接

sql 复制代码
-- 右外连接 right join
  select *|字段列表 from 右表 right [outer] join 左表 on 右表.字段 = 左表.字段 [五子句];
  如果数据不存在,右表记录会出现,而左表为null填充
例如:
select student.*, teacher.class as t_class, teacher.name as t_name 
from student right join teacher on student.class = teacher.class;

2.19、自然连接

sql 复制代码
--自然连接 natural join
自动判断连接条件完成连接.
  --自然内连接 natural inner join
  select *|字段列表 from 左表 natural [inner] join 右表;
  自然内连接其实就是内连接,这里的匹配条件是由系统自动指定.

  --自然外连接 natural outer join
  自然外连接分为自然左外连接和自然右外连接.匹配条件也是由系统自动指定.

  --自然左外连接 natural left join
  select *|字段列表 from 左表 natural left [outer] join 右表;
  
  --自然右外连接 natural right join
  select *|字段列表 from 右表 natural right [outer] join 左表;

2.10、子查询

sql 复制代码
/*子查询*/
子查询(内查询)在主查询(外查询)之前一次执行完成,子查询的结果被主查询使用.
使用子查询需用括号包裹.
select * 
from student 
where score=(select max(score) as max from student);--查询班级最高成绩学生的记录

根据子查询返回值的形式:
1.单一值: 返回单行单列的子查询,也叫标量子查询.
例如:select max(score) as max from student;

2.21、判断exists

sql 复制代码
--exists
--主要作用就是判断后面的select语句有没有查询到数据.结果为true有返回数据,否则就是false.
例如:select exists (select * from student where name ='uzi');--有

3、补充

3.1、三范式

sql 复制代码
/*数据库三范式*/
--建表规范
- 每个表保存一个实体信息
- 每个具有一个ID字段作为主键
- ID主键 + 原子表

--第一范式
字段不能再分,确保每列保持原子性.

--第二范式
满足第一范式的基础上,不能有部分依赖.
消除符合组合主键(A,B)就可以避免部分依赖. 增加单列关键字.

--第三范式
满足第二范式的基础上,不能有传递依赖.
某个字段依赖于主键,而有其他字段依赖于该字段. 这就是传递依赖.
将一个实体信息的数据放在一个表内实现

3.2、视图

视图是一张虚拟表,它表示一张表的部分数据和多张表的综合数据,视图的结构和数据都是建立在基表上.视图仅仅是一个表结构,视图的数据并不在数据库中存储,数据保存在基表中. 一张表可以创建多个视图.

视图作用:简化业务逻辑,对客户端隐藏真实的表结构

sql 复制代码
--创建视图
create [algorithm = undefined | merge | temptable] view 视图名称 [(字段列表)]
as
sql语句

语法解析:

1.视图名必须唯一,同时不能与表重名.

2.指定视图执行的算法,通过algorithm指定.

3.merge: 合并算法,将视图的语句和外层的语句合并后再执行.

4.temptable: 临时表算法,将视图执行的结果生成一张临时表,再执行外层语句.

5.undefined: 未定义型,用哪种算法有MySQL决定,默认算法merge.

6."字段列表"如果存在,数目必须等于select语句检索的列数

sql 复制代码
例如:
create view v_student (v_name,v_score)
as
select name,score from student where score >80;
sql 复制代码
--查看结构
show create view 视图名称

--删除视图
drop view [if exists] 视图名称
注意: 删除视图后,数据库中的数据依然存在.(对当前视图删除)

--修改视图结构 
alter view 视图名称 [(字段列表)]
as
sql语句

3.3、事物

事物:是并发控制的基本单位.事务就是一系列的操作,这些操作要么都执行,要么都不执行.(事务中可以保存多个SQL语句. 这些SQL语句是一个整体. 要么都执行,要么都不执行.)

sql 复制代码
--事务操作
  --开启事务
  start transaction; 或者 begin;
  --提交事务
  commit;
  --回滚事务
  rollback;

start transaction;--开启事物

insert into goods(goods_name,price) values('milk','43');
insert into goods(goods_name,price) values('bread','15');

commit;--提交事物

begin;--开启事物

insert into goods(goods_name,price) values('book','99');

rollback;--回滚事物

事务的特性

  • 原子性: 事务是一个不可分割的工作单位,事务中的操作要么都执行,要么都不执行.
  • 一致性: 事务前后数据的完整性必须保持一致. (事务开始和结束时,外部数据一致. 在整个事务过程中,操作是连续的.)
  • 隔离性: 多个用户并发访问数据库时,一个用户的事务不能被其它用户的事物所干扰,多个并发事务之间的数据要相互隔离.
  • 持久性: 一个事务一旦被提交,它对数据库中的数据改变就是永久性的.

事务的原理

利用InnoDB的自动提交(autocommit)特性完成. 普通的Mysql执行语句后,当前的数据提交操作均可被其它客户端可见.

事务是暂时关闭"自动提交"机制,需要commit提交持久化数据操作.

注意: 修改事务自动提交 set autocommit = 0 | 1 (0:取消自动提交;1:自动提交)--设置为不自动提交,因为Mysql默认自动提交执行.

3.4、用户权限管理

sql 复制代码
/*用户权限管理*/
用户信息表:mysql数据库的下, user表中
--创建用户
create user 用户名[@主机地址] identified by '密码';

例如:create user 'user_one'@'localhost' identified by '1234';--创建一个只能本机访问的用户
create user 'user_two'@'192.168.1.204.%' identified by '1234';--创建一个可以局域网访问的用户
create user 'user_three' identified by '1234';--创建一个可全网访问的用户
select host,user,password from user;--查看user表,host用户名和密码


--重命名用户
rename user 老用户名[@老主机地址] to 新用户名[@新主机地址];

-- 设置密码
set password = password('修改密码'); -- 为当前用户设置密码
set password for 用户名 = password('修改密码'); -- 为指定用户设置密码
例如:set password for 'user_three' = password('123456789'); -- 指定'user_three'用户设置密码

-- 删除用户
drop user 用户名[@主机地址];
例如:drop user 'user_two'@'192.168.1.204.%';

--分配权限给用户
grant 权限列表 on  *|库名 . *|表名  to 用户名[@主机地址] [identified by "用户密码"] [with grant option];

语法解析:
权限列表: all [privileges]: 表示所有权限; delete:允许使用delete; select:允许使用select; update:允许使用update; insert:允许使用insert 等...
 *.* :表示所有库的所有表
库名.表名 :表示某库下面的某表
例如: grant update,insert on *.* to user_one@'localhost' identified by "1234" with grant option;

--刷新权限
flush privileges;

--查看权限
show grants for 用户名[@主机地址];  
show grants for 'user_one'@'localhost';

--查看当前用户权限
show grants;

--撤消权限
revoke 权限列表 on *|库名 . *|表名 from 用户名[@主机地址];
revoke all privileges, grant option from 用户名[@主机地址];-- 撤销所有权限
例如:revoke update on *.* from 'user_one'@'localhost';
相关推荐
gma9991 小时前
Etcd 框架
数据库·etcd
爱吃青椒不爱吃西红柿‍️1 小时前
华为ASP与CSP是什么?
服务器·前端·数据库
Yz98761 小时前
hive的存储格式
大数据·数据库·数据仓库·hive·hadoop·数据库开发
武子康1 小时前
大数据-230 离线数仓 - ODS层的构建 Hive处理 UDF 与 SerDe 处理 与 当前总结
java·大数据·数据仓库·hive·hadoop·sql·hdfs
武子康2 小时前
大数据-231 离线数仓 - DWS 层、ADS 层的创建 Hive 执行脚本
java·大数据·数据仓库·hive·hadoop·mysql
黑色叉腰丶大魔王2 小时前
《MySQL 数据库备份与恢复》
mysql
苏-言2 小时前
Spring IOC实战指南:从零到一的构建过程
java·数据库·spring
Ljw...2 小时前
索引(MySQL)
数据库·mysql·索引
菠萝咕噜肉i2 小时前
超详细:Redis分布式锁
数据库·redis·分布式·缓存·分布式锁
长风清留扬2 小时前
一篇文章了解何为 “大数据治理“ 理论与实践
大数据·数据库·面试·数据治理