数据和信息
Data数据
任何描述事物的内容都可以称为数据
infomation信息
数据经过处理得到的内容称为信息。
数据库
DataBase,简称为DB。
运行在操作系统上,按一定的数据结构,保存数据的仓库,是一个电子化的文件柜,数据保存在硬盘中
数据库管理系统
DataBase Manager System,简称DBMS
通常所说的保存数据的仓库,是一个软件,称为数据库管理系统
常见的数据库管理系统
关系型数据库
数据局通过行row,列column的形式(表格)保存
每行称为一条记录
每列称为一个字段
数据之间有关联,能解决数据冗余
关系型数据库的特点
-
数据结构化的存储,方便保存和查询
-
支持复杂查询
-
海量数据的读写性能差
非关系型数据库
数据通过对象的形式保存,对象可以是一个键值对、文档、图片等
非关系型数据库的特点
-
保存数据的形式多样
-
对于海量收据的读写性能高
-
不支持复杂查询
MySQL常用控制命令
-
查看所有数据库
show databases;
-
切换数据库
use 数据库名;
-
查看当前数据库下的所有表
show tables;
-
创建一个数据库
create database test;
-
删除数据库
drop database 数据库名;
数据库管理系统图形化管理工具
如果只是用控制台操作数据库系统不方便,所有有很多图形化的管理工具
如navicat、datagrip、sqlyog等
Navicat15
创建数据库
在连接上点击右键,新建数据库,只需写数据库名
切换数据库
只需双击对应的数据库即可
创建数据表
在展开后的数据库中,在表的选项上新建数据表
保存表时会输入表面
创建表时的注意事项
-
每张表需要一个编号"id"列,通常设置为主键,目的是为了区分每条记录。整个主键列中的数据不能重复,通常还需要设置为自增
-
数据类型和所占长度根据实际情况选择
-
通过"不是null"设置能否允许该字段是否为空
-
如果某个字段有默认值,可以在设计表的时候设置,字符串用单引号引起来
-
最好写上注释
修改数据表
如果要对某张已存在的表进行修改,在对应的表上右键,设计表。
修改表时,要保存不影响现有数据
SQL
Structrued Query Language结构化查询语言
用于操作关系型数据库的一门语言,可以用来创建、维护数据库和数据
-- mysql中的注释
操作数据库
1.创建数据库
create database 数据库名;
2.切换数据库
use 数据库名;
3.删除数据库
drop database 数据库名;
操作数据表
1. 创建数据表
create table 表名(
字段名 数据类型 [字段特征],
字段名 数据类型 [字段特征],
……
字段名 数据类型 [字段特征]
)
2.删除数据表
drop table 表名;
3.修改数据表
-
对表重命名
alter table 旧表名 rename to 新表名;
-
添加新字段
alter table 表名 add column 字段名 数据类型 字段特征;
-
修改字段
alter table 表名 change 旧字段名 新字段名 数据类型 字段特征
-
删除字段
alter table 表名 drop 字段名;
数据完整性
数据完整性是指数据精确可靠,不能保存无意义或无效的数据。
如不合理的年龄、全为空的记录、重复记录等。
为了保证保存在数据库中的数据是完整数据,就要在设计数据表时添加一些约束或特征来保证数据完整性。
MySQL中常见的数据类型
整型 | ||
---|---|---|
tinyint | 短整型 | 对应java中的byte和short |
int | 整型 | 对应java中的int |
bigint | 长整型 | 对应java中的long |
浮点型 | ||
---|---|---|
float | 单精度浮点型 | 对应java中的float |
double | 双精度浮点型 | 对应java中的double |
decimal(宽度,精度) | 指定保留的小数位数和整体宽度 | 如decimal(4,2)3.1415926 --> 3.14 |
字符串 | ||
---|---|---|
char(长度) | 定长字符串 | char(10)表示占10个字符,就算保存了3个字符,也占10个字符,对应java中的的String |
varchar(长度) | 可变字符串 | varchar(10)表示最多占10个字符,保存了3个字符,就占3个字符,对应java中的String |
text | 文本 |
日期 | ||
---|---|---|
date | 日期 | yyyy-MM-dd |
time | 时间 | HH:mm:ss |
datetime | 日期时间 | yyyy-MM-dd HH:mm:ss |
timestamp(14或8) | 毫秒 | 保存日期的毫秒数.14表示yyyyMMddHHmmss,8表示yyyyMMdd |
约束
字段特征 | 概念 | 关键字 |
---|---|---|
非空约束 | 是否允许该字段为null | null表示可以为空,not null表示不可以为空 |
主键约束 | 主键(primary key)。用于区分表中的每条记录的一个字段。如果有现成的字段可以区分每条记录时,将该字段设置为主键字段。如果没有现成的字段可以区分每条记录时,通常会额外添加一个id字段用于设置为主键字段,通常一张表只有一个主键字段 | primary key |
唯一约束 | 保证该字段值不能重复 | unique |
默认值约束 | 如果在不给该字段添加数据的情况下,保证该字段有一个默认值 | default |
外键约束 | 在主从关系的表中,给从表的某个字段添加外键约束后,该字段的值只能来自于主表中的某个主键字段 | foreign key references |
添加约束
1.添加非空约束
alter table 表名 change 旧字段名 新字段名 数据类型 not null;
2.添加主键约束
alter table 表名 add primary key(字段名);
3.添加唯一约束
alter table 表名 add unique(字段名);
4.添加默认值约束
alter table 表名 alter 字段名 set default '默认值';
5.添加外键约束
alter table 从表表名 add foreign key(从表外键字段) references 主表(主表主键字段)
添加约束的操作通常是对已存在的表进行修改和维护时使用。如果是一张新表,最好在创建表的时候设计好约束
操作数据
数据的操作,是指数据的增加create、修改update、删除delete、查询read。
简称为CURD
数据添加insert
数据添加时,都是整行(一条记录),不能只给一个字段添加数据。
如果只给某个字段添加数据,实际是修改
给所有字段赋值
insert into 表名 values('值1','值2'...)
-
表名后无需添加字段名,添加时保证值的顺序和字段的顺序一致
-
遇到自增字段,不能省略不写,可以使用0或者null或者default让其自动填充,建议用null
-
遇到有默认值的字段,不能省略不写,使用default让其自动填充默认值
-
遇到允许为空的字段,不能省略不写,使用null让其设置为空
给指定字段赋值
insert into 表名(字段1,字段2,...) values('值1','值2',...)
-
没有默认值的非空字段必须写出来
-
表名后的字段顺序要和值的顺序一致
批量添加
可以使用
insert into 表名 values[字段1,字段2,...]
('值1','值2',....),
('值1','值2',....),
('值1','值2',....)
...
('值1','值2',....)
-
可以省略表名后的字段名
-
值的顺序和字段的顺序一致
-
如果一次添加多条记录,优先使用批量添加,效率更高
数据修改
修改单个字段的值
update 表名 set 字段名=值;
修改多个字段的值
update 表名 set 字段1='值',字段2='值',....
根据条件修改(where子句)
update 表名 set 字段='值' where 条件;
指定值
update 表名 set 字段= '值' where 字段 = '值'
指定范围
- 使用>、<、>=、<=表示范围,只用and、or、&&、||将多个条件
update 表名 set 字段 = '值' where 字段
- 使用"字段 between 值1 and 值2‘’表示字段在闭区间[值1,值2]
update 表名 set 字段='值' where 字段 between 值1 and 值2
- 使用!=或<>表示不等于
update 表名 set 字段='值' where 字段<>值
指定集合
- 在某个集合中 in
update 表名 set 字段 = '值' where 字段 in('值1','值2',...)
- 不在某个集合中 not in
update 表名 set 字段 = '值' where 字段 not in('值1','值2',...)
空值
- 使用is null表示空
update 表名 set 字段='值' where 字段 is null;
- 使用is not null表示非空
update 表名 set 字段='值' where 字段 is not null;
模糊查询
-- 字段 like '%娜%'
-- 带有娜字
-- 字段 like '张%'
-- 张字开头
--字段 like '%儿'
--儿字结尾
--字段 like '%瑞_'
--倒数第二个字为瑞
-- 字段 like '___'
-- 3个字
update 表名 set 字段='值' where 字段 like '%文字%'
数据删除delete
数据删除是删除一条或多条记录
删除所有
delete from 表名;
-- 或
truncate table 表名;
-
delete会保留自增列删除前的值,删除后再添加时,自动从删除前的值开始自增
-
truncate会重置自增项的值,效率更高
-
如果要删除主从关系且设置了外键的表中的数据,如果从表中有数据,不能直接删除
条件删除
delete from 表名 where 条件;
删除时的条件同修饰时的条件语句
数据查询select
查询所有字段
select * from 表名
查询指定字段
select 字段名1,字段名2,... from 表名
字段重命名
select 字段1 as '重命名',字段2 as '重命名',....from 表名;
查询指定记录
select * from 表名 limit 查询数量;
-- 下标m开始,查询查询数量调
select * from 表名 limit m,查询数量;
-- 每页显示size条,第page页
select * from 表名 limit (page-1)*size,size;
去重复
distinct
select distinct 字段名 from 表名;
条件查询
where子句,语法同修改、删除时的where
select * from 表名 where 条件;
排序
select * from 表名 where 条件 order by 排序字段 [ASC/DESC],排序字段 [ASC/DESC]....
-
排序可以是升序或降序
-
默认不写是升序排序ASC
-
降序需要些DESC
-
-
排序时如果有条件,where 条件 写到表名之后,排序之前
-
多字段排序时,在order by之后写多个字段及排序规则,用逗号隔开
- 按字段顺序优先排序
统计函数(聚合函数)
select 统计函数(字段名) from 表名;
函数 | |
---|---|
count(字段名) | 统计数量 |
sum(字段名) | 求和 |
avg(字段名) | 平均值 |
max(字段名) | 最大值 |
min(字段名) | 最小值 |
数学相关函数
函数 | 作用 |
---|---|
abs(值或字段) | 绝对值 |
pow(值或字段) | 次幂 |
sqrt(值或字段) | 开平方 |
round(值或字段) | 四舍五入 |
ceil(值或字段) | 向上取整 |
floor(值或字段) | 向下取整 |
字符串相关函数
函数名 | |
---|---|
length(字符串或字段) | 得到字符串长度 |
trim(字符串或字段)/ltrim(字符串或字段)/rtrim(字符串或字段) | 去掉字符串首尾/首/尾空格 |
left(字符串或字段,n)/right(字符串或字段,n) | 从字符串左/右开始截取n个字符 |
substr(字符串或字段,start) | 从start开始截取到末尾 |
substr(字符串,start,length) | 从start开始截取length长度 |
lcase()/ucase() | 转换小写/大写 |
instr(字符串1,字符串2)/locate(字符串2,字符串1) | 得到字符串2在字符串1中出现的顺序 |
reverse(字符串或字段) | 翻转字符串 |
concat(字符串1,字符串2…) | 拼接字符串 |
replace(字符串或字段,旧字符串,新字符串) | 将字符串中的旧字符串替换为新字符串 |
时间相关函数
函数 | 作用 |
---|---|
now() | 当前日期时间 |
current_date()/curdate() | 当前日期 |
current_time()/curtime() | 当前时间 |
year(日期)/month(日期)/day(日期) | 得到年/月/日部分 |
datediff(时间1,时间2) | 计算时间1与时间2相隔的天数 |
timediff(时间1,时间2) | 计算时间1和时间2相隔的时分秒 |
timestampdiff(指定单位,时间1,时间2) | 计算时间1和时间2之间相隔的指定时间单位,可以是year,month,day |
分组
select 分组字段,统计函数 from 表名 group by 分组字段;
按指定的字段进行分组,会将该字段值相同的记录归纳到同一局中。
分组通常配合统计函数使用。
如果统计函数作为条件,不能写在where之后,要写在having之后,
having子句放在分组之后。
-- 按图书类型分组,查询平均价格大于50的数据
select type_id,avg(book_price) from book_info group by type_id having avg(book_price)>50;
group_concat()函数
将分组后的数据拼接成字符串。
group_concat(字段1或字符串,字段2或字符串,....)
select group_concat(某字段) from 表名 group by 分组字段
-- 根据图书类型分组,查看每组下的图书名和作者名
select group.concat(book_name,'--',book_author) from book_info group by type_id
实际业务对应sql
登录
接收账号密码,查询用户表中是否存在记录
select from 表 where 账户=? and 密码=?
如果能查询到数据,说明存在该用户,可以登录。如果查询结果为null,说明用户名或密码错误
注册
接收账户密码,判断是否存在该账号,不存在则添加到用户表
select from 表 where 账号=?
insert into 表 values(null,账号,密码)
充值
登录成功后,修改余额字段
update 表名 set 余额=余额+充值金额 where 用户编号
删除
逻辑删除
不删除数据,只是不显示数据
可以给表中添加一个字段" 是否删除",用0表示为删除,用1表示已删除。
如果删除数据时,执行修改操作,将是否操作字段的值改为1
update 表名 set deleted=1 where 用户编号=?;
最终在查询所有时,加上"是否删除"=0条件
select * from 表 where deleted=0;
物理删除
真正将数据删除
delete from 表名 where 用户编号=?;
连接查询
交叉连接、笛卡尔积
将两张表中的数据两两组合,得到的结果就是交叉连接的结果,也称为笛卡尔积
集合A:{a,b}
集合B:{1,2,3}
集合A x 集合B={a1,a2,a3,b1,b2,b3}
select * from 表1,表2
select * from 表1 cross join 表2;
select * from 表1 inner join 表2;
将两张表中的数据互相组合成一张新表,其中有很多无效数据
内连接
select * from 表1,表2 where 表1.字段=表2.字段;
select * from 表1 inner join 表2 on 表1.字段=表2.字段
-- 如查询图书类型表(类型编号、类型名称)和图书详情表(图书编号、类型编号、图书名称)
select * from 图书类型表 t1,图书详情表 t2 where t1.类型编号=t2.类型编号
select * from 图书类型表 t1 inner join 图书详情表 t2 on t1.类型编号=t2.类型编号;
-
通常是通过主表的主键字段关联从表的外键字段
-
如果两张表中关联的字段名一致,一定要通过“表名.字段名”进行区分,通常给表重命名
-
如果使用inner join,带条件时需要加入where子句;如果使用,隔开各个表,带条件时使用and分隔条件
-
内连接只会显示两张表中有关联的数据
左连接
也叫左外连接
-- 在保证左表数据显示完整的情况下,关联右表中的数据,没有关联的数据用null表示
select * from 表1 left join 表2 on 表1.字段=表2.字段
-- 以上语句中表1称为左表,表2称为右表
右连接
-- 在保证右表数据显示完整的情况下,关联左表中的数据,没有关联的数据用null表示
select * from 表1 right join 表2 on 表1.字段=表2.字段
-- 以上语句中表1称为右表,表2称为左表
嵌套查询
将查询中的结果继续使用在另一个查询语句中
-- 查询大于平均价格的图书
select * from 表
where price>(select avg(price) from 表)
-- 根据作者分组,查询每组大于平均价格的图书
select * from 表 t1,
(select author,avg(price) avg_price from 表) t2
where t1.author=t2.author and price>avg_price
Jar
以.Jar为后缀的文件,称为java归档文件,保存的是java的字节码文件。
在java程序中导入某个.Jar文件,就能使用其中的class
JDBC
Java Database Connectivity Java 数据库连接
用于Java程序连接不同的数据库
实际在Java中定义的相关数据库连接时所需的接口,不同的数据库对其进行了实现。
核心接口
-
Connection:用于设置连接的数据库的地址、账号、密码
-
PreparedStatement:用于预处理,执行sql语句
-
ResultSet:用于接收查询后的数据
以上接口都来自于java.sql包下
SQL注入
在构造sql语句时,如果使用字符串拼接的方式构造动态sql,可能会造成sql注入的风险,导致执行的不是预期的sql语句
实体关系模型
实体Entity:一个表就是一个实体。
关系Relationship:实体与实体之间的关系。
实体关系模型也称为ER模型。
用图形表示ER模型时,这个图就称为ER图。
用矩形表示实体,用椭圆形表示实体的属性,用菱形表示实体之间的关系,用直线连接各个图形。
ER图
矩形:实体
椭圆形:实体的属性
菱形:实体之间的关系
实体关系分类
一对一:一个国家有一个领导人
1.根据两个实体创建两张表,都加上主键
2.在其中一张表中添加一个字段,保存另一张表的主键并设置唯一
一对多/多对一:一个班级有多个学生,一个学生不能有多个班级
1.先根据两个实体创建两张表,都加上主键
2.在从表中添加外键字段管理主表中的主键字段
多对多:一个学生学习多门课程,一门课程可以被多个学生学习
1.先根据两个实体创建两张表,都加上主键
2.创建第三张"关系"表,在该表中添加两个字段分别保存两个实体表中的主键
范式
第一范式1NF
字段不可再分
第二范式2NF
在满足1NF的基础上,消除部分依赖。
对于联合主键而言,所有非主属性字段必须完全依赖于主属性。
第三范式3NF
在满足2NF的基础上,消除传递依赖
视图View
视图可以当做数据库中的临时表,保存一些较为复杂的查询后的结果,之后可以直接通过查询该视图查询数据,不需要再次编写复杂的sql语句。
视图同时可以隐藏一些查询细节,定制查询数据。
创建视图
create view 视图名 as
查询的sql语句
使用视图
select * from 视图名
修改视图中的数据,会直接修改原始表中的数据
删除视图
drop view 视图名;
例
-- 查询平均分最高的课程名及其授课教师
-- 创建视图
create view myview as
select s.c_id,avg(cj) avg_cj from score s,course c where s.c_id=c.c_id group by s.c_id
-- 视图可以当做表使用
select c_name,t_name from teacher t1,teach t2,course c,
(select c_id from myview where avg_cj=
(select max(avg_cj) from myview)) t
where t1.t_id=t2.t_id and t.c_id=t2.c_id and c.c_id=t2.c_id
-- 表的行列转换
-- 查询每个学生的姓名、考试科目、成绩
create view test as
select s1.stu_id,stu_name,c_name,cj from student s1,course c,score s2
where s1.stu_id=s2.stu_id and s2.c_id=c.c_id
select * from test
select stu_id,stu_name,
sum(if(c_name='高等数学',cj,null)) as '高等数学',
sum(if(c_name='思修',cj,null)) as '思修',
sum(if(c_name='大学英语',cj,null)) as '大学英语',
sum(if(c_name='大学体育',cj,null)) as '大学体育'
from test group by stu_id
-- if(表达式,成立执行,不成立执行)
if(3>1,'xx','yy');
事务transaction
事务是由一组sql语句组成的执行单元,这些sql之间一般都互相依赖。
这个执行单元要么都执行,要么全部不执行。
如转账
1.select * from 表 where id=1 and money>1000;
2.update 表 set money=money-1000 where id=1;
3.update 表 set money=money+1000 where id=2;
以上的所有sql组成了一个转账的事务。
事务的特性ACID
原子性,一致性,隔离性,持久性
原子性Acomicity
事务是最小的执行单元。
一致性Consistency
事务执行前后,必须要所有的数据保存一致状态。(总体的数据守恒)
隔离性Isolation
事务并发时互相隔离,互不影响。
持久性Durability
事务一旦提交,对数据的改变是永久的
事务的使用
提交:commit
回滚:rollback
mysql中事务是默认自动提交的。
查看事务自动提交开启状态:
select @@autocommit 1表示开启自动提交,0表示关闭自动提交
设置事务自动提交状态
-- 设置事务不自动提交
set @@autocommit=0;
如果关闭了事务自动提交,在执行某个事务途中,如果出错,可以使用rollback回滚,让数据回到事务执行之前的状态。
如果不出错,通过commit提交事务,一旦提交事务,无法进行回滚。
手动提交事务
1.关闭事务自动提交: set @@autocommit
2.开启事务:start transaction;
3.事务执行的sql
4.没有提交之前,如果要回滚,使用rollback;
5.如果要提交,使用commit; 一旦提交,无法rollback
事务并发可能出现的问题
在同一时刻同时执行多个事务时,称为事务的并发。
事务并发会有可能出现以下问题
问题 | 描述 |
---|---|
脏读 | 事务A读取到了事务B还未提交的数据 |
不可重复读 | 事务A中如果要读取两次数据,在这期间,事务B对数据进行了修改并提交,导致事务A读取两次的情况不一致 |
幻读 | 事务A读取读取1 |
事务的隔离级别
为了防止事务并发时出现以上各种问题,数据库中设计了几种事务与事务之间的隔离级别。
隔离级别 | 能否出现脏读 | 能否出现不可重复读 | 能否出现幻读 |
---|---|---|---|
Read Uncommitted未提交读RU | 会 | 会 | 会 |
Read Committed已提交读RC(Oracle默认) | 不会 | 会 | 会 |
Repeatable Read可重复读RR(MySQL默认) | 不会 | 不会 | 会 |
Serializable可序列化 | 不会 | 不会 | 不会 |
查看事务隔离级别
select @@transaction_isolation
设置事务隔离级别
set [session|global] transaction isolation level
[read uncommitted|repeatable read|read committed|serializable]
触发器trigger
如果要在更新某张表之前或之后,自动执行另一组sql时,可以使用触发器实现。
如表A是客户表,表B是操作日志表,对表A进行更新操作时,将操作的记录记录在表B中
慎用触发器,因为如果有10000条记录,在修改记录时,触发器就会执行10000次,会花费很多时间
创建触发器
create trigger 触发器名
触发时机 触发操作 on 表 for each row
begin
满足触发时机时自动执行的sql;
end
在向customer表中添加一条记录后,自动在log表中添加一条记录
create trigger mytrigger
after insert on customer for each row
begin
insert into log values(null,'插入一条数据',now());
end
使用触发器
触发器一旦创建成功,无需刻意调用,在执行相应的操作时,自动执行触发器
-- 只对customer表做插入操作,就会自动对log表添加记录
insert into customer values(null,'test','123456',0,null)
删除触发器
drop trigger 触发器名
存储过程procedure
类似于java中的方法,定义一组用于完成特定功能的sql语句。
定义存储过程后,通过调用存储过程名,就可以执行定义的内容
存储过程可以有参数
调用存储过程
-- 调用无参数的存储过程
call 存储过程名();
-- 调用输入型参数存储过程
call 存储过程名('实参');
-- 调用输出型参数存储过程
call 存储过程名(@变量)
-- 调用输入输出型参数存储过程
set @变量
call 存储过程名(@变量)
定义存储过程
create procedure 存储过程名([参数类型 参数名 参数数据类型])
-- 参数类型分为输入型/输出型/输入输出型
begin
sql语句;
end
无参数
create procedure 存储过程名()
begin
sql语言;
end
输入型参数
create procedure 存储过程名(in 形参名 数据类型)
begin
sql语句;
end
输出型参数
create procedure 存储过程名(out 形参名 数据类型)
begin
sql语句;
--通常需要将查询出的结果通过into赋值给形参
end
-- 根据作者查询图书数量
create procedure myproc3(in zz varchar(20),out count int)
begin
-- into表示将查询的结果保存到参数上行的count中
select count(book_id) into count from book_info where book_author=zz;
end
-- 调用,@xxx表示将存储过程的输出型参数进行保存到变量xxx中
call myproc3('刘慈溪',@count);
-- 查询参数中保存的数据
select @count;
输入输出型参数
create procedure 存储过程名(inout 形参名 数据类型)
begin
sql语句;
end
-- 查询书名中带有指定文字的图书名、作者和类型
create procedure myproc4(inout b varchar(20))
begin
select book_name,book_author,type_name from book_info bi,book_type bt where bi.type_id=bt.type_id and book_name like concat('%',b,'%');
end
set @b='龙';
call myproc4(@b);
select @b;
删除存储过程
drop procedure 存储过程名;
MySQL编程
在定义存储过程中,可以定义变量、使用流程控制语句
定义变量
create procedure 存储过程名()
begin
--declare 变量名 数据类型
declare num int;
declare name varchar(20);
end
给变量赋值
create procedure 存储过程名()
begin
declare num int;
--给num赋值
-- select 字段/值 into 变量 [from 表]
select 123 into num;
select book_name into name from book_info where book_id=1;
end
读取变量的值
create procedure 存储过程名()
begin
declare num int;
select 123 into num;
select book_name into name from book_info where book_id=1;
-- select 变量
select num;
select name;
end
-- 创建存储过程
create procedure myproc5()
begin
-- 定义变量
declare sum_num int;
-- 给变量赋值
select sum(book_num) into sum_num from book_info;
-- 打印变量的值
select sum_num;
end
call myproc5();
条件语句
写在存储过程里
单分支if语句
if 条件
then
满足条件时执行的sql;
end if;
多分支 if语句
if 条件
then
满足条件时执行的sql;
else
满足条件时执行的sql;
end if;
case语句(相当于java的switch)
case 变量
when 值 then
满足该值时候执行;
when 值 then
满足该值时候执行;
else
没有任何满足时执行;
end case;
循环语句
while循环
while 条件 do
满足条件时执行的内容;
end while;
-- 使用循环添加10个用户
create procedure myproc9()
begin
-- 定义循环变量
declare num int;
-- 给变量赋值
select 1 into num;
-- 循环添加数据
while num<=10 do
insert into customer values(null,concat('测试数据',num),'123123',0,null);
set num=num+1;
end while;
end
call myproc9();
repeat循环
repeat
满足条件时执行的内容;
until 条件 end repeat;
create procedure myproc10()
begin
declare i int;
select 50 into i;
repeat
insert into customer values(null,concat('测试数据',i),'123123',0,null);
set i=i+1;
until i=60 end repeat;
end
call myproc10()
loop循环
循环名:loop
循环体;
if 条件 then leave 循环名;
end if;
end loop;
-- 使用loop循环
create procedure myproc11()
begin
declare num int;
select 100 into num;
-- 开始loop循环
test:loop
insert into customer values(null,concat('测试数据',num),'123123',0,null);
set num=num-1;
if num=90 then leave test;
end if;
end loop;
end
-- 调用
call myproc11();
MySQL核心内容
SQL语句
-
数据库和数据表的创建、修改、删除
-
数据完整性(约束)
-
单表增删改查CURD
-
函数
-
多表查询、嵌套查询
数据库设计
-
实体关系模型(ER)
-
ER图
-
范式
JDBC
-
l连接MySQL所需jar文件
-
普通java工程需要手动导入jar文件
-
maven项目需要依赖自动导入jar文件
-
-
MySQl驱动名
//mysql5.5之前版本 Class forName("com.mysql.jdbc.Driver"); //mysql8以后版本 Class.forName("com.mysql.jdbc.cj.Driver");
-
写数据库帮助类 util类 连接数据库的字符串
-
String url="jdbc:mysql://localhost:端口号/数据库名?serverTimezone=Asia/Shanghai"; String username="账号名"; String password="密码"
-
事务
-
事务的概念和特性(原子性,一致性,隔离性,持久性)
-
事务的隔离级别
-
事务并发时出现的问题
-
脏读
-
不可重复读
-
幻读
-
-
事务的隔离级别
-
read uncommitted 可能会出现脏读、不可重复读、幻读 效率最高
-
read committed 解决了脏读
-
repeatable read MySQL默认 解决了脏读和不可重复读
-
serializable 解决了所有问题,效率最低
-
存储引擎
-
MySQL5.5版本之前,默认使用MyIsam存储引擎,不支持事务
-
**MySQL5.5版本之后,默认使用InnoDB存储引擎,支持事务