一、1.MySQL的存储引擎
储存引擎的类型:MyISAM、InnoDB、 Memory、CSV等九种
MyiSAM和InnoDB类型主要区别
名称 | InnoDB | MyISAM |
事务处理 | 支持 | 不支持 |
数据行锁定 | 支持 | 不支持 |
外键约束 | 支持 | 不支持 |
全文索引 | 不支持 | 支持 |
表空间大小 | 较大,约2倍 | 较小 |
适用场合
<1>使用MyISAM:不需事务,空间小,以查询访问为主
<2>使用InnoDB:多删除,更新操作, 安全性高,事务处理及并发控制
2.查看当前默认储存引擎
语法:SHOW VARIABLES LIKE'storage_engine%':
执行命令得
修改存储引擎
修改my.ini配置文件
语法:default-storage-engine=InnoDB(改为其他存储存储)
设置表的存储引擎
语法:CREATE TABLE 表名(#省略代码)ENGINE=存储引擎;
CREATE TABLE test_mysam(
tit INT
)ENGINE=MYISAM;
执行命令得
默认为InnoDB存储引擎 两个引擎的不同 会使表中存储数据时的格式不同
3.数据表的存储位置
<1>MyISAM类型表文件
*.frm:表结构定义文件
*.MYD:数据文件
*.MYI:索引文件
<2>InnoDB类型表文件
*.frm:表结构定义文件
ibdata1文件
注意!!!
存储位置 (因操作系统而异,可查my.ini)
二、DML语句
Data Manipulation Language,数据操纵语言,命令使用户能够查询数据库以及操作已有数据库中的数据的计算机语言。具体是指是SELECT查询、UPDATE更新、INSERT插入、DELETE删除。
1.插入单条数据纪录
语法:INSERT IN TO 表名 (字段名列表) VALUES (值列表);
注意!!!
<1>字段名是可选的,如省略则依次插入所有字段
<2>多个列表和多个值之间是用逗号隔开
<3>值列表和字段名列表一一对应
<4>如果插入的是表中部分数据,字段名列表必填
例:
USE python7;
INSERT INTO `student`(`studentNo`,`loginPwd`,`studentName`,`gradeId`,`phone`,`bornDate`)
VALUES(30013,'123','黄小平',1,'13956799999','1996-5-8');
执行命令得
2.插入多调数据记录
语法:INSERT INTO 新表(字段名列表)
VALUES(值列表1),(值列表2),......,(值列表n);
(为避免表结构发生变化引发的错误,建议插入数据时写明具体字段名)
例:
CREATE TABLE SUBJECT(
subjectNo INT(4) PRIMARY KEY AUTO_INCREMENT,
subjectName VARCHAR(50),
classHour INT(4),
gradeID INT(4)
)
INSERT INTO `subject`(`subjectName`,`classHour`,`gradeID`)
VALUES('Logic Java',220,1),('HTML',160,1),('Java OOP',230,2);
执行命令得
3.将查询结果插入新表
语法:CREATE TABLE 新表( SELECT (值列表1),值列表2)...(值列表n) FROM 旧表);
例:编写SQL语句实现从学生表提取姓名、手机号两列数据存储到通讯录表中
方法一:如果新列表已经存在将会报错
CREATE TABLE phoneList(
SELECT studentName,phone FROM student
);
方法二:phoneList必须存在 其中列的数据类型和原表的数据类型一致
给表添加新增列:先给表添加主键然后属性为新增
CREATE TABLE phoneList(
studentName VARCHAR(50) NOT NULL,
phone VARCHAR(50) DEFAULT NULL)
INSERT INTO phoneList()
SELECT
studentName,phone
FROM student
执行命令得
4.数据更新
语法:UPDATE 表名
SET 字段1=值1 , 字段2=值2,...,字段n=值n
[WHERE 条件]
例:
UPDATE student SET sex='男';
#不添加条件则全部变为男性
UPDATE student SET gradeID=3,loginPwd=123456#年级编号 密码改变
WHERE studentNo>20010#条件为学号>20010的学生
执行命令得
5.数据删除
语法:DELETE FROM 表名 [WHERE 条件];
TRUNCATE TABLE 表名;
(TRUNCATE语句删除后将重置自增列,表结构及其字段、约束、索引保持不变,执行速度比DELETE语句块)
例:
DELETE FROM phoneList
WHERE studentName='郭靖'#删除名为郭靖的行
执行命令得
三、查询
查询产生一个虚拟表
看到的是表形式显示的结果,但结果并不真正存储
每次执行查询只是从数据表中提取数据,并按照表的形式显示出来
1.查询全部的行和列
语法:SELECT * FROM student
2.查询部分列
语法:SELECT `studentNo`,`studentName`,`address`
FROM `student`
WHERE `address='天津市河西区'`
3.使用AS命名列
SELECT `studentNo` AS' 学生编号',`studentName` AS '学生姓名',
`address `AS 学生地址
FROM `student`
WHERE `address` ='天津市河西区';
代码:
SELECT studentNo AS '学号',studentName AS '姓名',phone AS '手机',address AS '地址',bornDate AS '出生日期'
FROM `student`
WHERE gradeID=1#条件为班级编号1的学生
执行命令得
4.查询空行
语法:SELECT `studentName` FROM `student` WHERE `email` IS NULL;
代码
UPDATE student SET email=666
WHERE loginPwd=123
SELECT `studentName` FROM `student` WHERE `email` IS NULL;
执行代码得
使用常量列
为每条数据添加一个常量列
SELECT *,'北京信息中心' AS '学校名称' FROM `student`
WHERE gradeID>1
执行命令得
四、常用函数
1.聚合函数
函数名 | 作用 |
AVG() | 返回某字段的平均值 |
COUNT() | 返回某字段的行数 |
MAX() | 返回某字段的最大值 |
MIN() | 返回某字段的最小值 |
SUM() | 返回某字段的和 |
例
:
SELECT AVG(`studentResult`) AS '平均成绩',
COUNT(*) AS '参加人数',
MAX(studentResult) AS '最高',
MIN(studentResult) AS '最低',
SUM(studentResult) AS '总和'
FROM result
执行命令得
2.字符串函数
函数名 | 作用 | 举例 |
CONCAT(str1,str1...strn) | 字符串连接 | SELECT CONCAT('My','S','QL'); |
INSERT(str,pos,len,newstr) | 字符串替换 | SELECT INSERT( |
LOWER(str) | 将字符串转为小写 | SELECT LOWER('MySQL'); |
UPPER(str) | 将字符串转为大写 | SELECT UPPER('MySQL'); |
SUBSTRING(str,num,len) | 字符串截取 | SELECT SUBSTRING( |
例:
#字符串连接
SELECT CONCAT('北','京','海','淀');
#字符串替换 (原,开始,长度,新)
SELECT INSERT('北京市',1,2,'运城');
#替换大小写
SELECT LOWER('Hello');
SELECT UPPER('Hello');
#字符串截取
SELECT SUBSTRING('hello mysql',7,5)
分别执行命令的
3.时间日期函数
函数名 | 作用 | 举例(结果与当前时间有关) |
CURDATE() | 获取当前日期 | SELECT CURDATE(); |
CURTIME() | 获取当前时间 | SELECT CURTIME(); |
NOW() | 获取当前日期和时间 | SELECT NOW(); |
WEEK(date) | 返回日期date为一年中的第几周 | SELECT WEEK(NOW()); |
YEAR(date) | 返回日期date的年份 | SELECT YEAR(NOW()); |
HOUR(time) | 返回时间time的小时值 | SELECT HOUR(NOW()); |
MINUTE(time) | 返回时间time的分钟值 | SELECT MINUTE(NOW()); |
DATEDIFF(date1,date2) | 返回日期参数date1和date2之间相隔的天数 | SELECT DATEDIFF(NOW(), |
ADDDATE(date,n) | 计算日期参数date加上n天后的日期 | SELECT ADDDATE(NOW(),5); |
例:
SELECT CURDATE()#获取当前日期
SELECT CURTIME()#获取当前时间
SELECT NOW()#获取当前日期和时间
SELECT WEEK(NOW())#返回日期为一年中的第几周
SELECT YEAR(NOW())#返回日期的年份
SELECT HOUR(NOW())#返回时间的小时数
SELECT MINUTE(NOW())#返回时间的分钟数
SELECT DATEDIFF(NOW(),'2020-8-8')#返回两个日期之间的相隔的天数
SELECT ADDDATE(NOW(),100)#计算日期参数now加上100天后的日期
4.数学函数
函数名 | 作用 | 举例 |
CEIL(x) | 返回大于或等于数值x的最小整数 | SELECT CEIL(2.3) |
FLOOR(x) | 返回小于或等于数值x的最大整数 | SELECT FLOOR(2.3) |
RAND() | 返回0-1的随机数 | SELECT RAND() |
例:
SELECT CEIL(2.3)#返回大于或等于数值为2.3的最小整数
SELECT FLOOR(2.3)#返回小于或等于数值为2.3的最大整数
SELECT RAND()#返回0-1之间的随机数
五、1.ORDER BY子句
ORDER BY 子句实现按一定顺序显示查询结果(ASC:升序 DESC:降序)
例:把成绩都降低10%后加5分,再查询及格成绩,并按照成绩从高到低排序
SELECT studentNo AS '学生编号',`studentResult`*(1-0.1)+5 AS '综合成绩'
FROM `result`
WHERE `studentResult`*(1-0.1)+5>=60
ORDER BY `studentResult` DESC
执行命令得
2.LIMIT子句
MySQL查询语句中使用LIMIT子句限制结果集 (做分页)
语法:SELECT <字段名列表>
FROM <表名或视图>
[WHERE <查询条件>]
[GROUP BY <分组的字段名>]
[ORDER BY <排序的列名>[ASC 或 DESC]]
[LIMIT [位置偏移量,]行数]; / LIMIT ((页数-1)*条数),条数;
例如:
SELECT studentNo AS '学生编号',`studentResult`*(1-0.1)+5 AS '综合成绩'
FROM `result`
WHERE `studentResult`*(1-0.1)+5>=60
ORDER BY `studentResult` DESC
LIMIT 2,3#从数据的第二行开始读取三行
执行命令得
练习:
查询所有年级密码为123的学员信息,按学号升序排序
显示每页2条
显示第2页,即从第3条数据开始显示2条数据
SELECT studentNo AS '学生编号',`studentName` AS '姓名',`phone` AS '电话'
FROM `student`
WHERE `loginPwd`=123
ORDER BY `studentNo`
LIMIT 2,2
执行命令得
不加LIMIT句子
加上LIMIT句子
3.子查询
子查询是一个潜逃在SELECT 、INSERT、UPDATE、或DELETE语句或其他子查询中的查询
子查询在WHERE语句中的一般用法
语法:SELECT...FROM 表名 WHERE 字段 比较运算符 (子查询)
注意:
将子查询和比较运算符联合使用,必须保证子查询返回的值不能多于一个
例:编写SQL语句,查看年龄比'黄小平'晓得学生,要求显示这些学生的信息
分析:
第一步:查询得到'黄小勇'的出生日期
第二步:利用where语句,筛选出生日期比'黄小平'大的学生
(此方法为父查询)
通过子查询实现
SELECT *
FROM `student`
WHERE `bornDate`>(
SELECT `bornDate` FROM `student` WHERE `studentName`='黄小平'
)
执行命令得
练习1
需求说明
1.查询2016年2月17日考试前5名的学员的学号和分数
2.将所有女学生按年龄从大到小排序,从第2条记录开始显示6名女学生的姓名、年龄、出生日期、手机号信息
3.按出生年份分组统计学生人数,将各组中人数达到2人的年份和人数显示出来
4.查询参加2016年2月17日考试的所有学员的最高分、最低分、平均分
1.
SELECT `studentNo`,`studentResult`
FROM `result`
WHERE `examDate`='2016-02-17 00:00:00'
2.
SELECT `studentName` AS '姓名',`bornDate` AS '年龄',`phone` AS '手机'
FROM `student`
ORDER BY `bornDate`
LIMIT 1,6
3.
SELECT YEAR(bornDate)AS 年份, COUNT(studentNo) AS 人数
FROM student
GROUP BY 年份
HAVING 人数>2
4.
SELECT MAX(`studentResult`),MIN(`studentResult`),AVG(`studentResult`)
FROM `result`
WHERE `examDate`='2016-02-17 00:00:00'
练习2
<1>查询参加最近一次Logic Java考试成绩的学生的最高分和最低分
#查询参加最近一次Logic Java考试成绩的学生的最高分和最低分
SELECT MAX(studentResult),MIN(studentResult)
FROM result
WHERE examDate=(SELECT MAX(examDate)
FROM result
WHERE `subjectNO`=(SELECT subjectNo FROM `subject` WHERE subjectName='Logic Java'))
AND `subjectNO`=(SELECT subjectNo FROM `subject` WHERE subjectName='Logic Java')
执行命令得
IN子查询
常用IN替换等于(=)的子查询
IN后面的子查询可以返回多条记录 (IN 相当于 or的操作)
<2>查询“Logic Java”课程考试成绩为60分的学生名单
#查询“Logic Java”课程考试成绩为60分的学生名单
SELECT *
FROM student
WHERE studentNo IN (SELECT studentNo
FROM result
WHERE studentResult=60
AND subjectNo=(SELECT subjectNo FROM `subject` WHERE subjectName='Logic Java')
)
执行命令得
<3>查询参加“Logic Java”课程最近一次考试的在读学生名单
实现步骤:
1.获得“Logic Java”课程的课程编号
2.根据课程编号查询得到“Logic Java”课程最近一次的考试日期
3.根据课程编号和最近一次的考试日期查询出学生编号
4.获得“Logic Java”课程的在读年级编号
SELECT *
FROM student
WHERE gradeID=(SELECT gradeID FROM `subject` WHERE subjectName='Logic Java' )#Logic Java的在读年级编号
AND studentNo IN (
SELECT studentNo
FROM result
WHERE subjectNo=(#最近一次Logic Java考试的学生编号
SELECT subjectNo FROM `subject` WHERE subjectName='Logic Java')#Logic Java的课程编号
AND examDate=(SELECT MAX(examDate)
FROM result
WHERE `subjectNO`=(SELECT subjectNo FROM `subject` WHERE subjectName='Logic Java'))#最近一次考试时间
)
执行命令得
NOT IN 子查询
<4>查询未参加“Logic Java”课程最近一次考试的在读学生名单
SELECT *
FROM student
WHERE gradeID=(SELECT gradeID FROM `subject` WHERE subjectName='Logic Java' )#Logic Java的在读年级编号
AND studentNo NOT IN (
SELECT studentNo
FROM result
WHERE subjectNo=(#最近一次Logic Java考试的学生编号
SELECT subjectNo FROM `subject` WHERE subjectName='Logic Java')#Logic Java的课程编号
AND examDate=(SELECT MAX(examDate)
FROM result
WHERE `subjectNO`=(SELECT subjectNo FROM `subject` WHERE subjectName='Logic Java'))#最近一次考试时间
)
<5>查询获得年级名称是S1的所有课程的课程编号
根据课程编号查询课程表得到课程名称
SELECT `subjectName` FROM `subject` WHERE `gradeId` IN (
SELECT `gradeId` FROM `grade` WHERE `gradeName`='S1'
)