Mysql(2)

3 MySQL数据管理

3.1 外键

外键概念

如果公共关键字在一个关系中是主关键字,那么这个公共关键字被称为另一个关系的外键。由此可见,外键表示了两个关系之间的相关联系。以另一个关系的外键作主关键字的表被称为主表,具有此外键的表被称为主表的从表

在实际操作中,将一个表的值放入第二个表来表示关联,所使用的值是第一个表的主键值(在必要时可包括复合主键值)。此时,第二个表中保存这些值的属性称为外键(foreign key)。

外键作用

保持数据一致性完整性,主要目的是控制存储在外键表中的数据,约束。使两张表形成关联,外键只能引用外表中的列的值或使用空值。

外键所在的表是从表 引用的字段所在的表就是主表

创建表成功后,添加外键约束

CREATE TABLE `student` (
  `id` int(4) NOT NULL AUTO_INCREMENT COMMENT '学号',
  `name` varchar(30) NOT NULL DEFAULT '匿名' COMMENT '姓名',
  `pwd` varchar(20) NOT NULL DEFAULT '123456' COMMENT '密码',
  `sex` varchar(2) NOT NULL DEFAULT '女' COMMENT '性别',
  `birthday` datetime DEFAULT NULL COMMENT '出生日期',
  `gradeid` int(10) NOT NULL COMMENT '学生的年级',
  `address` varchar(100) DEFAULT NULL COMMENT '家庭住址',
  `email` varchar(50) DEFAULT NULL COMMENT '邮箱',
  PRIMARY KEY (`id`),
  KEY `FK_gradeid` (`gradeid`),
  CONSTRAINT `FK_gradeid` FOREIGN KEY (`gradeid`) REFERENCES `grade` (`gradeid`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8

-- 创建表的时候没有外键关系 (另加外键关系)
ALTER TABLE `student`
ADD CONSTRAINT `FK_gradeid` FOREIGN KEY(`gradeid`) REFERENCES `grade`(`gradeid`);

删除外键

删除grade表,报错 (student 是子表。grade是主表)

注意 : 删除具有主外键关系的表时 , 要先删子表 , 后删主表

3.2 DML语言(全部记住)

  • INSERT (添加数据语句)
  • UPDATE (更新数据语句)
  • DELETE (删除数据语句)

3.3 添加

INSERT INTO 表名[(字段1,字段2,字段3,...)] VALUES('值1','值2','值3')

注意事项:

  • 字段或值之间用英文逗号隔开 .
  • ’ 字段1,字段2…’ 该部分可省略 , 但添加的值务必与表结构,数据列,顺序相对应,且数量一致 .
  • 可同时插入多条数据 , values 后用英文逗号隔开 .

3.4 修改

UPDATE 表名 SET column_name=value [,column_name2=value2,...] [WHERE 条件];

3.5 删除

delete命令

DELETE FROM 表名 [WHERE condition];  

truncate 命令

作用:完全清空一个数据库表,表的结构和索引约束不会变!

delete和truncate的区别

  • 相同点:都能删除数据,但都不会删除表结构

  • 不同:

    • truncate 重新设置 自增列 计数器会归零

    • truncate 不会影响事务

      DELETE FROM `test` -- 不会影响自增 
      TRUNCATE TABLE `test` -- 自增会归零
      

delete删除的问题==,重启数据库,现象

  • innoDB 自增列会从1开始(存在内存当中的,断电即失)
  • MyISAM 继续从上一个自增量开始(存在文件中的,不会丢失)

4 DQL查询数据(最重点!)

4.1 DQL(Data Query Language)

数据库最核心的语言

-- 查询所有学生信息
SELECT * FROM student;
-- 查询指定列(学号 , 姓名)
SELECT studentno,studentname FROM student;

4.2 指定查询字段

去重 distinct

作用:去除select查询结果中重复的数据,重复的数据只显示一条

-- # 查看哪些同学参加了考试(学号) 去除重复项
SELECT * FROM result; -- 查看考试成绩
SELECT studentno FROM result; -- 查看哪些同学参加了考试
SELECT DISTINCT studentno FROM result; -- 了解:DISTINCT 去除重复项 , (默认是ALL)

数据库的列(表达式)

select 表达式 from 表

-- selcet查询中可以使用表达式
SELECT @@auto_increment_increment; -- 查询自增步长
SELECT VERSION(); -- 查询版本号
SELECT 100*3-1 AS 计算结果; -- 表达式

-- 学员考试成绩集体提分一分查看
SELECT studentno,StudentResult+1 AS '提分后' FROM result;

4.3 where条件子句

作用:检索数据中符合条件的值

搜索的条件由一个或者多个表达式组成!结果为 布尔值

SELECT `StudentNo`,`StudentResult` FROM result
WHERE studentresult BETWEEN 95 AND 100

模糊查询:比较运算符

在这里插入图片描述

LIKE

-- 查询姓刘的同学的学号及姓名
-- like结合使用的通配符 : % (代表0到任意个字符) _ (一个字符)
SELECT studentno,studentname FROM student
WHERE studentname LIKE '刘%';

-- 查询姓刘的同学,后面只有一个字的
SELECT studentno,studentname FROM student
WHERE studentname LIKE '刘_';

-- 查询姓刘的同学,后面只有两个字的
SELECT studentno,studentname FROM student
WHERE studentname LIKE '刘__';

-- 查询姓名中含有 嘉 字的
SELECT studentno,studentname FROM student
WHERE studentname LIKE '%嘉%';

IN

-- 查询学号为1000,1001,1002的学生姓名
SELECT studentno,studentname FROM student
WHERE studentno IN (1000,1001,1002);

null

-- 查询出生日期没有填写的同学
-- 不能直接写=NULL , 这是代表错误的 , 用 is null
SELECT studentname FROM student
WHERE BornDate IS NULL;

-- 查询出生日期填写的同学
SELECT studentname FROM student
WHERE BornDate IS NOT NULL;

-- 查询没有写家庭住址的同学(空字符串不等于null)
SELECT studentname FROM student
WHERE Address='' OR Address IS NULL;

4.4 联表查询

JOIN 对比

img
-- 查询参加了考试的同学(学号,姓名。科目编号。分数)
SELECT * FROM student
SELECT * FROM result
/*
 1. 分析查询的字段来自那些表(如果不是同一张表,则需要联接查询)
 2. 确定使用哪种联接查询?7种
 确定交叉点
 判断的条件:学生表中的studentno = 成绩表 studentno
 */
 
 -- join (连接的表)on(判断的条件) 联接查询
 -- where 等值查询
 -- on条件是生成临时表时使用的条件,它不管on中的条件是否为真,都会返回左边表中的记录,还会返回on条件为真的记录
 -- where条件是在临时表生成好后,再对临时表进行过滤的条件,此时已经没有left join的含义(必须返回左边表的记录)了,条件不为真    的就全部过滤掉
 SELECT s.studentno,studentname,subjectno,studentresult 
 FROM student AS s
 INNER JOIN result AS r 
 WHERE s.studentno = r.studentno
 # s.studentno 指student中的学号,避免ambiguous
 # inner join 查看并集
操作描述
inner join如果表中至少有一个匹配,就返回
left join即使右表中没有匹配,也会从左表中返回所有的值 # e.g:王凯没有成绩,依旧返回
right join即使左表中没有匹配,也会从右表中返回所有的值 # 右表result中没有王凯的成绩,所以没有返回
-- left join 
-- 查询缺考的同学
 SELECT s.studentno,studentname,subjectno,studentresult 
 FROM student s
 LEFT JOIN result r
 ON s.studentno = r.studentno
 WHERE studentresult IS NULL
 
 -- 思考题(查询了参加考试的同学信息:学号,学生姓名,科目名,分数)
 /*
 1. 分析查询的字段来自那些表(studentno,studentname,subjectname,studentresult)
 2. 确定使用哪种联接查询?7种
 确定交叉点
 判断的条件:学生表中的studentno = 成绩表 studentno
 */
 SELECT  s.studentno,studentname,subjectname,studentresult
 FROM student s 
 RIGHT JOIN result r
 ON r.studentno = s.studentno
 INNER JOIN `subject` sub
 ON r.subjectno = sub.subjectno
 
from a left join b #以左表为基准
from a right join b #以右表为基准

-- 查询学员所属的年级(学号,学生姓名,年级名称)
 SELECT  studentno,studentname,gradename
 FROM student s
 INNER JOIN `grade` g
 ON s.gradeid = g.gradeid
 
-- 查询科目所属的年级(科目名称,年级名称)
 SELECT  subjectname,gradename
 FROM `subject` sub
 INNER JOIN grade g
 ON sub.gradeid = g.gradeid

-- 思考题(查询了 参加数据库结构-1 数据库考试的同学信息:学号,学生姓名,科目名,分数)
SELECT s.studentno,studentname,subjectname,studentresult
FROM student s
INNER JOIN result r
ON s.studentno = r.studentno
INNER JOIN `subject` sub
ON r.subjectno = sub.subjectno
WHERE subjectname = '数据库结构-1'

– 我要查询哪些数据 select…

– 我从哪几个表查 from 表 xxx join 连接的表 on 交叉条件

–假设存在一种多张表查询,慢慢来,先查询两张表再慢慢增加

自连接(了解)

自己和自己的表连接,核心:一张表拆为两张一样的表即可

-- 查询父子信息:把一张表看为两个一模一样的表
SELECT a.`categoryname` AS '父栏目',b.`categoryname` AS '子栏目'
FROM `category` AS a,`category` AS b
WHERE a.`categoryid` = b.`pid`

4.5 分页和排序

排序

– 排序:升序 ASC 降序:DESC

-- 排序:升序 ASC 降序:DESC
SELECT s.studentno,studentname,subjectname,studentresult
FROM student s
INNER JOIN result r
ON s.studentno = r.studentno
INNER JOIN `subject` sub
ON r.subjectno = sub.subjectno
ORDER BY studentresult ASC

分页

– 分页:每页只显示五条数据

–语法:limit 当前页,页面的大小

–limit 0,5 1~5

–limit 1,5 2~6

/*============== 分页 ================
语法 : SELECT * FROM table LIMIT [offset,] rows | rows OFFSET offset
好处 : (用户体验,网络传输,查询压力)

推导:
   第一页 : limit 0,5
   第二页 : limit 5,5
   第三页 : limit 10,5
   ......
   第N页 : limit (pageNo-1)*pagesize,pagesize
   [pageNo:页码,pageSize:单页面显示条数]
   
*/

-- 每页显示5条数据
SELECT s.studentno,studentname,subjectname,StudentResult
FROM student s
INNER JOIN result r
ON r.studentno = s.studentno
INNER JOIN `subject` sub
ON r.subjectno = sub.subjectno
WHERE subjectname='数据库结构-1'
ORDER BY StudentResult DESC , studentno
LIMIT 0,5

4.6 子查询

-- 使用子查询(由里及外)
SELECT studentno,subjectno,studentresult
FROM result
WHERE subjectno = (
	SELECT subjectno FROM `subject`
	WHERE subjectname= '数据库结构-1'
)

4.7 Select语法

SELECT [ALL | DISTINCT]
{* | table.* | [table.field1[as alias1][,table.field2[as alias2]][,...]]}
FROM table_name [as table_alias]
  [left | right | inner join table_name2]  -- 联合查询
  [WHERE ...]  -- 指定结果需满足的条件
  [GROUP BY ...]  -- 指定结果按照哪几个字段来分组
  [HAVING]  -- 过滤分组的记录必须满足的次要条件
  [ORDER BY ...]  -- 指定查询记录按一个或多个条件排序
  [LIMIT {[offset,]row_count | row_countOFFSET offset}];
   -- 指定查询的记录从哪条至哪条

注意 : [ ] 括号代表可选的 , { }括号代表必选

指定查询字段

-- 查询表中所有的数据列结果 , 采用 **" \* "** 符号; 但是效率低,不推荐 .

-- 查询所有学生信息
SELECT * FROM student;

-- 查询指定列(学号 , 姓名)
SELECT studentno,studentname FROM student;
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值