mysql基础语法——个人笔记

news2024/12/23 4:20:58

0 前言

以前学习且实践过mysql,但后来用得少,随着岁月更替,对其印象渐浅,所以每次需要用时,都会去再看一眼语法规范,然后才能放心动手操作

然而,在信息爆炸的时代,查语法规范时,检索出来的资料总是五花八门,有时需要看好几篇资料,才能汇总得出完整的、准确的、符合自己语言习惯的信息,这一过程费时费力

鉴于此,本文将根据笔者个人语言习惯,基于mysql8.0.39,整理包括数据、表、库、用户(根据个人使用频率进行的排序)的增、删、改、查基础语法(不涉及数据库安装相关的内容),以节省以后查资料的时间(“自己做的饭,吃着放心”),同时也期待能对读者在mysql基础语法的笔记整理和学习方面有所帮助

(附上mysql官网语法文档链接:https://www.mysqlzh.com/doc/124.html)

1 数据相关

1.1 创建数据

创建数据,其实就是向表中添加/插入数据,默认会向表的最后一条数据之后进行插入

语法:

# (1)插入单条全量数据
# 注意:
#     插入全量数据(表名称后面未指定全量字段)时,即使字段值为null,也需指定null值,
# 否则会报错
#     需要按表结构中字段先后顺序来依次指定字段值
INSERT INTO 数据表名称 
VALUES (字段1的值, 字段2的值, ..., 字段N的值);
# (2)插入单条部分数据
# 注意:
#     插入部分数据时,表名称后面指定的字段必须包括非空字段,并需要进行传值;空字段可
# 以指定也可以不指定,指定时为指定值,不指定时为空值或默认值
#     可以在数据表名称后面将字段先后顺序颠倒并对应指定值,但不建议这样做(不规范)
INSERT INTO 数据表名称 (字段a, 字段b, ...) 
VALUES (字段a的值, 字段b的值, ...);
# (3)插入多条数据
# 插入多条数据时,不管是全量还是部分数据,依旧需要遵循上面的注意事项
INSERT INTO 数据表名称 (根据全量或部分,选择是否指定字段)
VALUES 
(字段1-值1, 字段2-值1, ..., 字段N-值1), 
(字段1-值2, 字段2-值2, ..., 字段N-值2), 
... 
(字段1-值N, 字段2-值N, ..., 字段N-值N);

示例:

假设已经有了一个users表,其建表语句如下:

CREATE TABLE `users` (
                         `id` SMALLINT(10) NOT NULL COMMENT '用户ID',
                         `name` VARCHAR(50) DEFAULT NULL COMMENT '用户姓名',
                         `contact` VARCHAR(100) DEFAULT NULL COMMENT '用户联系方式',
                         `createTime` DATETIME NOT NULL COMMENT '用户创建时间',
                         `freeze` TINYINT(1) NOT NULL COMMENT '用户是否被冻结',
                         PRIMARY KEY (`id`) USING BTREE,
                         UNIQUE INDEX `IDX_USERS_CONTACT` (`contact`) USING BTREE,
                         INDEX `IDX_USERS_NAME` (`name`) USING BTREE
) ENGINE = InnoDB 
CHARACTER SET = utf8mb4 
COLLATE = utf8mb4_general_ci 
COMMENT = '用户表';

现需要对此表分别实现1条全量数据和2条部分数据的创建

 (1)创建1条全量数据
INSERT INTO `users` 
VALUES (10000001, '张三', '123456789@qq.com', '2024-08-28 08:08:08', 0);
# (2)创建2条部分数据
# now()是mysql常用的内置函数之一,用于获取当前mysql服务端的时间,其他常用函数可见本文附页5.1章节的内容
INSERT INTO `users` (`id`, `createTime`, `freeze`) 
VALUES 
(10000002, now(), 0), 
(10000003, now(), 0);

验证:

Step1:看执行命令后能否得到Query OK的响应

Step2:查看数据是否成功创建

SELECT * FROM `users`;

1.2 修改数据

语法:

# (1)修改单个字段
UPDATE 数据表名称 
SET 字段 = 值 
WHERE 筛选条件;
# (2)修改多个字段
UPDATE 数据表名称 
SET 字段1 = 值1, 字段2 = 值2, ... 
WHERE 筛选条件;

示例:

# (1)将users表中张三的联系方式,修改为18888888888
UPDATE `users` 
SET contact = '18888888888' 
WHERE name = '张三';
# 查看数据是否修改成功
SELECT * FROM `users`;
# (2)将users表中姓名为null且freeze为0的内容,修改为name='未知',freeze=1
UPDATE `users` 
SET name = '未知', freeze = 1
WHERE name is null and freeze = 0;
# 查看数据是否修改成功
SELECT * FROM `users`;

1.3 查询数据

1.3.1 基础查询

语法:

SELECT 字段名称 
FROM 数据表名称 
WHERE 筛选条件;

(1)字段名称:多个字段可用英文逗号分隔,用*可代表全部字段

(2)运算符:可在SELECT和WHERE后面添加运算符,常见的运算符可见本文附页5.4章节的内容

备注:如何用LIKE模糊查询来查出包含%的数据值?

答案:在代表数据值的%前面加转义符(\)即可

示例:

假设已经有了一个student表,其建表语句以及表数据如下:

CREATE TABLE `student` (
                         `id` BIGINT(20) NOT NULL AUTO_INCREMENT COMMENT '学生ID',
                         `name` VARCHAR(50) NOT NULL COMMENT '学生姓名',
                         `class` VARCHAR(10) DEFAULT NULL COMMENT '学生班级',
                         `chinese` DECIMAL(4,1) NOT NULL COMMENT '语文成绩',
                         `math` DECIMAL(4,1) NOT NULL COMMENT '数学成绩',
                         PRIMARY KEY (`id`) USING BTREE
) ENGINE = InnoDB 
CHARACTER SET = utf8mb4 
COLLATE = utf8mb4_general_ci 
COMMENT = '学生表';

INSERT INTO `student` 
VALUES (1, '李伟', '三班', 98.0, 95.0);
INSERT INTO `student` 
VALUES (2, '李国栋', '一班', 68.0, 88.0);
INSERT INTO `student` 
VALUES (3, '刘小丽', '一班', 76.0, 54.5);
INSERT INTO `student` 
VALUES (4, '王思琪', '二班', 34.0, 81.0);
INSERT INTO `student` 
VALUES (5, '荆涛', '二班', 88.0, 66.0);
INSERT INTO `student` 
VALUES (6, '王勇', '一班', 86.0, 97.5);
INSERT INTO `student` 
VALUES (7, '王浩', '三班', 52.0, 41.0);
INSERT INTO `student` 
VALUES (8, '张新宇', '三班', 95.0, 98.0);
INSERT INTO `student` 
VALUES (9, '王大拿', '二班', 78.0, 84.0);

现需要对此表分别实现全量数据和部分条件数据的查询:

(1)查询student表有多少条数据
SELECT COUNT(*) FROM `student`;
(2)查询student表的全部数据
SELECT * FROM `student`;
(3)查询总共有哪几个班级
SELECT DISTINCT class FROM `student`;
(4)查询三班语文成绩的平均分
SELECT AVG(chinese) FROM `student` WHERE class='三班';
(5)查询一班和二班所有学生的数学成绩最高分
SELECT MAX(math) FROM `student` WHERE class IN ('一班','二班');
(6)查询语文成绩在80-100,且数学成绩在60-100的学生信息
SELECT * FROM `student` 
WHERE (chinese BETWEEN 80 AND 100) AND (math BETWEEN 60 AND 100);

1.3.2 高级查询

语法:

SELECT 字段名称 
FROM 数据表名称 
WHERE 筛选条件 
GROUP BY 分组字段名 
HAVING 分组后结果的筛选条件 
ORDER BY 排序字段名 排序规则(ASC|DESC)
LIMIT 数据行数;

初始化数据:

假设已经有了这三个表,其建表语句以及表数据如下:

CREATE TABLE `dept` (
    `deptno` TINYINT not null,
    `dname` VARCHAR(14)
);
INSERT INTO `dept` VALUES (10, 'ACCOUNTING');
INSERT INTO `dept` VALUES (20, 'RESEARCH');
INSERT INTO `dept` VALUES (30, 'SALES');
INSERT INTO `dept` VALUES (40, 'OPERATIONS');
INSERT INTO `dept` VALUES (50, 'HR');
INSERT INTO `dept` VALUES (60, NULL);

CREATE TABLE `emp` (
    `empno` int,
    `ename` VARCHAR(10),
    `job` VARCHAR(9),
    `mgr` int,
    `hiredate` DATE,
    `sal` float(7,2),
    `comm` float(7,2),
    `deptno` TINYINT
);
INSERT INTO `emp` VALUES (7369, 'SMITH', 'CLERK', 7902, '1980-12-17', 8000, null, 20);
INSERT INTO `emp` VALUES (7499, 'ALLEN', 'SALESMAN', 7698, '1981-02-20', 16000, 300, 30);
INSERT INTO `emp` VALUES (7521, 'WARD', 'SALESMAN', 7698, '1981-02-22', 12500, 500, 30);
INSERT INTO `emp` VALUES (7566, 'JONES', 'MANAGER', 7839, '1981-04-02', 29750, null, 20);
INSERT INTO `emp` VALUES (7654, 'MARTIN', 'SALESMAN', 7698, '1981-09-28', 12500, 1400, 30);
INSERT INTO `emp` VALUES (7698, 'BLAKE', 'MANAGER', 7839, '1981-05-01', 28500, null, 30);
INSERT INTO `emp` VALUES (7788, 'SCOTT', 'ANALYST', 7566, '1987-04-19', 30000, null, 20);
INSERT INTO `emp` VALUES (7839, 'KING', 'PRESIDENT', null, '1981-11-17', 50000, null, 10);
INSERT INTO `emp` VALUES (7844, 'TURNER', 'SALESMAN', 7698, '1981-09-08', 15000, 0, 30);
INSERT INTO `emp` VALUES (7876, 'ADAMS', 'CLERK', 7788, '1987-05-23', 11000, null, 20);
INSERT INTO `emp` VALUES (7900, 'JAMES', 'CLERK', 7698, '1981-12-03', 9500, null, 30);
INSERT INTO `emp` VALUES (7902, 'FORD', 'ANALYST', 7566, '1981-12-03', 30000, null, 20);
INSERT INTO `emp` VALUES (7934, 'MILLER', 'CLERK', 7782, '1982-01-23', 13000, null, 10);

create table `salgrade`(
    `grade` int(11)  comment '工资等级',
    `losal` int(11)  comment '最低工资',
    `hisal` int(11)  comment '最高工资'
);
INSERT INTO `salgrade` VALUES (1, 7000, 12000);
INSERT INTO `salgrade` VALUES (2, 12010, 14000);
INSERT INTO `salgrade` VALUES (3, 14010, 20000);
INSERT INTO `salgrade` VALUES (4, 20010, 30000);
INSERT INTO `salgrade` VALUES (5, 30010, 99990);
1.3.2.1 group by

在mysql中,group by被广泛应用于需要对数据进行分组统计的查询场景(COUNT(*)其实就相当于一个没有筛选条件的group by)

以实际工作、学习、生活中的场景进行举例:

【工作】对于一个存放了公司的所有员工基本信息的数据表,需要根据不同的业务部门进行分组,查询每个部门有多少人

【学习】对于一个存放了学校所有学生成绩的数据表,需要根据不同的班级来进行分组,查询每个班的各科成绩平均分、最高分、最低分

【生活】对于一个存放了菜市场销售信息的数据表,需要根据粮、油、果、蔬这些不同的商品进行分组,查询每类商品的平均单价、平均销量、总销售额

示例:

查询在员工表(emp表)中,各工作岗位(job)分别有多少人,薪资的最大值、最小值以及平均值分别是多少

SELECT job, COUNT(*) AS `岗位人数` , MAX(sal) AS `岗位最高薪资`, MIN(sal) AS `岗位最低薪资`, AVG(sal)  AS `岗位平均薪资`  
FROM `emp` 
GROUP BY job;

结果:

1.3.2.2 having

having与where的用法类似,都是做条件筛选,不同点:

  • where在group by之前,having在group之后

  • where是先过滤后聚合, having是先聚合后过滤(where是直接做条件筛选,having是根据group by的结果做条件筛选)

  • 用AS可以取别名,但where条件一般不能用别名,having条件可以用别名

以实际工作、学习、生活中的场景进行举例:

【工作】对于一个存放了公司的所有员工基本信息的数据表,用group by根据不同的业务部门进行了分组,查出了每个部门有多少人,现需要针对查询结果加筛选:查出部门人数大于50的部门及对应的部门人数

【学习】对于一个存放了学校所有学生成绩的数据表,用group by根据不同的班级进行了分组,查出了每个班的各科成绩平均分、最高分、最低分,现需要针对查询结果加筛选:查出各科成绩平均分>80,最高分=100,最低分<60的班级及对应的各科成绩平均分、最高分、最低分

【生活】对于一个存放了菜市场销售信息的数据表,用group by根据粮、油、果、蔬这些不同的商品进行了分组,查出了每类商品的平均单价、平均销量、总销售额,现需要针对查询结果加筛选:查出每类商品平均单价<8,平均销量>100,总销售额>800的食品及对应的各类商品平均单价、平均销量、总销售额

示例:

查询在员工表(emp表)中,工作岗位(job)人数大于>3、最高薪资<=20000、最低薪资>=10000薪资的岗位以及岗位人数、最高薪资、最低薪资和平均薪资

SELECT job, COUNT(*) AS `岗位人数` , MAX(sal) AS `岗位最高薪资`, MIN(sal) AS `岗位最低薪资`, AVG(sal)  AS `岗位平均薪资`  
FROM `emp` 
GROUP BY job 
HAVING `岗位人数` > 3 and `岗位最高薪资` <= 20000 and `岗位最低薪资` >= 10000;

结果:

1.3.2.3 order by + aes|desc

在mysql中,order by被广泛应用于需要对查询结果集(也可以用别名)进行排序的场景,通常需要结合aes(升序)、desc(降序)来进行使用

以实际工作、学习、生活中的场景进行举例:

【工作】对于一个存放了公司的所有员工基本信息的数据表,需要查询每个项目经理的项目回款总额和项目验收数量并降序显示,方便根据业绩进行年终奖发放

【学习】对于一个存放了学校所有学生成绩的数据表,需要查询每个学生的总分并降序显示,方便根据分数进行荣誉奖项发放

【生活】对于一个存放了菜市场销售信息的数据表,需要查询每个商品的单价并升序显示,方便菜市场公告每日最便宜的几个商品

示例:

将员工表(emp表)中各员工薪资(sal)以降序形式进行查询显示

SELECT * 
FROM `emp` 
ORDER BY sal DESC;

结果:

1.3.2.4 limit & 语法综合实践

在mysql中,limit被广泛应用于获取select查询结果集特定行数的场景(注:limit是起始值默认是从0开始的)

比如:

在web开发中,通常会使用分页查询的方式,来在每一页显示用户所需的多少行数据内容,此时可以用limit来进行处理

在对员工业绩进行排序之后,分别查询出业绩最高和最低的前5名员工信息

示例:

查询在员工表(emp表)中,上级领导(mgr)不为null(除老板之外),工作岗位(job)人数大于>1,平均薪资排名前3名的岗位以及岗位人数、平均薪资

SELECT job, COUNT(*) AS `岗位人数` ,AVG(sal)  AS `岗位平均薪资`  
FROM `emp` 
WHERE mgr is not null 
GROUP BY job 
HAVING `岗位人数` > 1 
ORDER BY `岗位平均薪资` desc
LIMIT 3;

结果:

1.3.5 连接查询

在实际的各类信息系统开发过程中,如果把所有数据都放到一个数据表里面,那么不仅会使insert数据很麻烦,还会影响数据的查询效率以及安全性,所以一般会将各类不同的数据分开到不同的数据表中进行存放,并在数据表中将有关系的字段做关联,形成完善的数据体系

在单个数据表中查询某字段是很容易的,如果要分别查询不同数据表中的不同字段,那就分别对这些数据表进行多次select即可;但如果要将多次select的结果汇总到一起进行显示,那就需要用到连接查询了

连接查询,一般是指将多个数据表通过特定的关联关系连接在一起,并将这些数据表中所需要的各字段汇总得出查询结果

比如:

我在外卖平台点了一份【青椒肉丝】,在外卖系统中,可能会有以下几张表:

(1)商家信息表:存放商家本身的信息,包括商家店名、门店地址、联系电话等数据

(2)商家菜单表:存放商家菜单的信息,包括菜品名称、菜品图片、菜品价格等数据

(3)骑手信息表:存放骑手本身的信息,包括骑手姓名、骑手头像、联系电话等数据

(4)订单信息表:存放订单记录的信息,包括食物列表、订单金额、配送时间等数据

当我点开“配送详情”时,外卖平台就可以将上面四张表关联到一起(商家菜单与商家门店做关联、订单食物列表与商家菜品名称做关联、骑手信息与订单做关联),让我能看到商家店名、食物列表、菜品价格、配送时间等从这些表中汇总得出的信息

连接查询一般分为外连接和内连接两种方式:

  • 外连接:一个表与另外一个表之间进行连接

  • 内连接:一个表与这个表本身之间进行连接

1.3.5.1 外连接

外连接一般有左连接、右连接以及交差连接三种方式

(1)左连接:left join on

语法:

SELECT 字段名称 
FROM 左表 LEFT JOIN 右表 
ON 左右两表字段关联关系;

左连接,是以左表数据为基准,通过关联关系,查询出右表中对应的数据,并与左表数据汇总到一起得到查询结果

当左表中的某数据没有一个与之相对应的右表数据时,左表中此数据仍然会显示在查询结果中,右表中对应字段值为空

示例:

在薪资等级表(salgrade)中,通过最低值(losal)和最高值(hisal)的区间,来判断工资属于哪一级(grade)

要求:根据员工表(emp)中薪资(sal)在薪资等级表(salgrade)中哪段区间,来查询得出各员工的工资等级信息

SELECT e.ename AS `姓名`, e.sal AS `薪资`, s.grade AS `薪资等级` 
FROM `emp` AS e LEFT JOIN `salgrade` AS s 
ON e.sal BETWEEN s.losal AND s.hisal;

结果:

(2)右连接:right join on

语法:

SELECT 字段名称 
FROM 左表 RIGHT JOIN 右表 
ON 左右两表字段关联关系;

右连接,是以右表数据为基准,通过关联关系,查询出左表中对应的数据,并与左表数据汇总到一起得到查询结果

当右表中的某数据没有一个与之相对应的左表数据时,右表中此数据仍然会显示在查询结果中,左表中对应字段值为空

示例:

左连接示例中的LEFT改成RIGHT,观察结果

SELECT e.ename AS `姓名`, e.sal AS `薪资`, s.grade AS `薪资等级` 
FROM `emp` AS e RIGHT JOIN `salgrade` AS s 
ON e.sal BETWEEN s.losal AND s.hisal;

结果:

(3)交叉连接 cross join

语法:

SELECT 字段名称 
FROM 左表 CROSS JOIN 右表;

交叉连接,是将左右两表数据全部都连接一次(笛卡尔积),可以用where加判断条件

示例:

将部门表(dept)和薪资等级表(salgrade)进行连接,排列组合得到每个部门可能有哪些薪资等级方案

SELECT * 
FROM `dept` CROSS JOIN `salgrade`;

结果:

1.3.5.2 内连接

语法:

SELECT 字段名称 
FROM 左表 INNER JOIN 右表 
ON 左右两表字段关联关系;

注意,对于内连接:

(1)INNER可以省略,即:单写JOIN,不写INNER、LEFT、RIGHT、CROSS,也能代表内连接,但建议写上,这样可读性会更好

(2)ON也可以省略,如果省略,则和CROSS JOIN类似,是得到笛卡尔积,但不建议这么做,笛卡尔积还是用CROSS JOIN,这样可读性会更好

示例:

在员工表(emp)中,存放了每个员工的信息,然而,在一个公司内,员工之间也会存在上下级关系,现需要查询存在上级领导的员工,其上级领导(mgr)是谁

SELECT e1.*, e2.empno AS `领导编号`, e2.ename AS `领导姓名` 
FROM `emp` AS e1 INNER JOIN `emp` AS e2 
where e1.mgr = e2.empno;

结果:

1.3.5 子查询 + any|all

子查询,其实就是嵌套查询,通常是把某个查询的结果作为一个条件、一个值或者一个临时表来放到where或者from后进行使用,能将复杂的查询逻辑以一种易于理解的方式进行表示

子查询通常可以和any(任一)、all(全部)结合起来进行使用

示例1:

查询出薪资比销售部门(dname=SALES)任何一名员工都要高的所有员工的信息

# 写法1
SELECT * 
FROM `emp` 
WHERE sal > (SELECT MAX(sal) 
             FROM `emp` 
             WHERE deptno = (SELECT deptno 
                             FROM `dept` 
                             WHERE dname = 'SALES'));
# 写法2(使用ALL代替MAX)
SELECT * 
FROM `emp` 
WHERE sal > ALL(SELECT sal 
             FROM `emp` 
             WHERE deptno = (SELECT deptno 
                             FROM `dept` 
                             WHERE dname = 'SALES'));

结果:

备注:嵌套里面的select叫做子查询,嵌套外面的select叫做主查询,执行顺序是:从最里面的子查询开始依次往外进行查询

示例2:

查询每个部门(emp表中deptno字段)的平均薪资(emp表中AVG(sal))是什么薪资等级(salgrade表中grade字段)

# 先对于emp表查询deptno,avg(sal),将查询结果作为临时表,连接salgrade表输出结果
SELECT e.deptno, s.grade 
FROM (SELECT deptno,AVG(sal) AS ag FROM `emp` GROUP BY deptno) AS e
INNER JOIN `salgrade` AS s
ON ag BETWEEN losal AND hisal;

1.3.6 union

在mysql中,union操作符用于合并两个或多个select语句的结果集,并返回唯一的结果集(将查询结果进行去重汇总再后返回)

注意,使用union时:

  • 要求两个select语句的结果必须是相同字段、相同先后顺序、相同字段列数

  • 默认会进行去重(用union all可以保留所有数据,不去重)

语法:

SELECT 字段名称 from 数据表1名称 
UNION 
SELECT 字段名称 from 数据表2名称;

示例:

假设已经有了2个数据表,分别存放两个学院的教师信息(teacher_medicine表存放医药学院的教师信息,teacher_computer表存放计算机学院的教师信息),其建表语句以及表数据如下:

CREATE TABLE `teacher_medicine` (
                         `id` BIGINT(20) NOT NULL AUTO_INCREMENT COMMENT '教师ID',
                         `name` VARCHAR(50) NOT NULL COMMENT '教师姓名',
                         `tno` VARCHAR(50) NOT NULL COMMENT '教师编号',
                         `class` VARCHAR(10) DEFAULT NULL COMMENT '学生班级',
                         PRIMARY KEY (`id`) USING BTREE
) ENGINE = InnoDB 
CHARACTER SET = utf8mb4 
COLLATE = utf8mb4_general_ci 
COMMENT = '医药学院教师表';

INSERT INTO `teacher_medicine` 
VALUES (1, '李伟', 't036', '三班');
INSERT INTO `teacher_medicine` 
VALUES (2, '李国栋', 't008', '一班');
INSERT INTO `teacher_medicine` 
VALUES (3, '刘小丽', 't153', '一班');
INSERT INTO `teacher_medicine` 
VALUES (4, '王思琪', 't096', '二班');

CREATE TABLE `teacher_computer` (
                         `id` BIGINT(20) NOT NULL AUTO_INCREMENT COMMENT '教师ID',
                         `name` VARCHAR(50) NOT NULL COMMENT '教师姓名',
                         `tno` VARCHAR(50) NOT NULL COMMENT '教师编号',
                         `class` VARCHAR(10) DEFAULT NULL COMMENT '学生班级',
                         PRIMARY KEY (`id`) USING BTREE
) ENGINE = InnoDB 
CHARACTER SET = utf8mb4 
COLLATE = utf8mb4_general_ci 
COMMENT = '计算机学院教师表';

INSERT INTO `teacher_computer` 
VALUES (1, '张伟', 't066', '三班');
INSERT INTO `teacher_computer` 
VALUES (2, '李国栋', 't008', '一班');
INSERT INTO `teacher_computer` 
VALUES (3, '刘思琪', 't099', '一班');
INSERT INTO `teacher_computer` 
VALUES (4, '王小丽', 't147', '二班'); 

现需要查出两个学院的全部教师名称和教师编号

SELECT name, tno from `teacher_medicine` 
UNION 
SELECT name, tno from `teacher_computer`;

结果:

由于“李国栋”老师在两个学院都任教,所以合并查询后自动去重,只出现一次

1.3.7 exists

在mysql中,exists被广泛应用于检查各种信息是否存在记录的场景,存在则返回1,不存在则返回0

应用场景示例:

# (1)检查数据库/数据表是否存在,不存在则创建数据库/数据表
CREATE TABLE IF NOT EXISTS `test`(`id` int);
# (2)检查select结果集是否存在
SELECT EXISTS(SELECT * FROM `emp` where empno = 666);
# (3)当子查询返回的是一个不确定的值集合时,EXISTS可以作为IN子句的替代,
SELECT * FROM `emp` AS o 
WHERE EXISTS (SELECT * FROM `dept` AS d 
              WHERE d.deptno = o.deptno);

1.4 删除数据(任何删除操作均需谨慎,请勿删数据跑路)

语法:

# (1)删除数据表中指定数据
DELETE FROM 数据表名称 
WHERE 筛选条件;
# (2)删除数据表中全部数据
TRUNCATE TABLE 数据表名称;

示例:

# (1)删除users表中联系方式为null的数据
DELETE FROM `users` 
WHERE contact is null;
# 查看数据是否删除成功
SELECT * FROM `users`;
# (2)删除users表中全部数据
TRUNCATE TABLE `users`;
# 查看数据是否删除成功
SELECT * FROM `users`;

2 表相关

2.1 创建数据表

语法(常用字段):

CREATE TABLE 数据表名称 (
    字段名称1 字段数据类型1 字段约束1 COMMENT '字段描述1',
    ...
    字段名称n 字段数据类型n 字段约束n COMMENT '字段描述n',
    表级约束1,
    ...
    表级约束n
) ENGINE 存储引擎 
CHARACTER SET 字符集 
COLLATE 排序规则 
其他规则 
COMMENT='表的描述';

(1)建议用反引号(``)包裹数据表名称和字段名称,这样可以更好的支持数据表和字段名称中出现特殊字符

(2)常见的字段数据类型可见本文附页5.2章节的内容

(3)常见的字段约束和表约束可见本文附页5.3章节的内容

(4)存储引擎、字符集、排序规则为非必填

存储引擎、字符集、排序规则如果不设置,则会采取mysql配置文件(my.cnf/my.ini)中的设置;如果在mysql配置文件中也没有设置,则会采取mysql本身的默认设置(此设置根据mysql版本不同而所有差异,具体可以在mysql官方网站查询,但建议在建表语句或者配置文件二选一,这样更清晰)

示例:

创建一个名为users的表,要求:

(1)有5个字段,各字段有类型和约束要求

  • 用户ID字段,类型为数值,最大20位,要求字段非空

  • 用户姓名字段,类型为字符,最大不超过50位,如果不填值则默认为空

  • 用户联系方式字段,类型为字符,最大不超过100位,如果不填值则默认为空

  • 用户创建时间字段,类型为日期,要求字段非空

  • 用户是否冻结字段,类型为1位数的数值,用0标识未冻结,1标识已冻结,要求字段非空

  • 用户ID字段是主键,每个用户的联系方式均唯一,用户的姓名字段加索引,表中所有索引使用B-tree

(2)存储引擎用INNODB、字符集用utf8mb4,排序规则用utf8mb4_general_ci

# 先用use命令选中数据库,才能操作对应的数据表(假设已经有了一个名为lctest的实例库)
use lctest;
# 执行建表语句
CREATE TABLE `users` (
                         `id` BIGINT(20) NOT NULL COMMENT '用户ID',
                         `name` VARCHAR(50) DEFAULT NULL COMMENT '用户姓名',
                         `contact` VARCHAR(100) DEFAULT NULL COMMENT '用户联系方式',
                         `createTime` DATETIME NOT NULL COMMENT '用户创建时间',
                         `freeze` TINYINT(1) NOT NULL COMMENT '用户是否被冻结',
                         PRIMARY KEY (`id`) USING BTREE,
                         UNIQUE INDEX `IDX_USERS_CONTACT` (`contact`) USING BTREE,
                         INDEX `IDX_USERS_NAME` (`name`) USING BTREE
) ENGINE = InnoDB 
CHARACTER SET = utf8mb4 
COLLATE = utf8mb4_general_ci 
COMMENT = '用户表';

验证:

Step1:看执行命令后能否得到Query OK的响应

Step2:查看数据表是否已创建

SHOW TABLES;

Step3:查看表结构

SHOW CREATE TABLE `users`;

2.2 修改数据表

对于数据表的修改,通常是新增、删除或修改表中的字段名称、字段数据类型或字段约束

语法:

# (1)修改字段名称
ALTER TABLE 数据表名称 
CHANGE COLUMN 旧的字段名称 新的字段名称 字段数据类型 COMMENT '字段描述';
# (2)修改字段数据类型
ALTER TABLE 数据表名称 
MODIFY COLUMN 字段名称 新的字段数据类型 COMMENT '字段描述';
# (3)修改字段约束
ALTER TABLE 数据表名称 
MODIFY COLUMN 字段名称 字段数据类型 新的字段约束 COMMENT '字段描述';
# (4)添加字段
ALTER TABLE 数据表名称 
ADD COLUMN 新的字段名称 新的字段数据类型 新的字段约束 COMMENT '新字段的描述',
# (5)删除字段
ALTER TABLE 数据表名称 
DROP COLUMN 字段名称;
# (6)添加索引
ALTER TABLE 数据表名称 
ADD INDEX 索引名称 (索引字段);
# (7)删除索引
ALTER TABLE 数据表名称 
DROP INDEX 索引名称;
# (8)添加主键
ALTER TABLE 数据表名称 
ADD PRIMARY KEY (索引字段);
# (9)删除主键
ALTER TABLE 数据表名称 
DROP PRIMARY KEY;

示例:

# (1)给users表新增用户年龄字段,类型为数值,最大3位,要求字段非空
ALTER TABLE `users` 
ADD COLUMN `age` TINYINT(3) NOT NULL COMMENT '用户年龄';
# 查询是否添加正确
SHOW CREATE TABLE `users`;
# (2)将users表freeze字段的约束条件由NOT NULL改为NOT NULL DEFAULT 0
ALTER TABLE `users` 
MODIFY COLUMN `freeze` TINYINT(1) NOT NULL DEFAULT 0 COMMENT '用户是否被冻结';
# 查询是否修改正确
SHOW CREATE TABLE `users`;
# (3)将users表name字段改名为username
ALTER TABLE `users` 
CHANGE COLUMN `name` `username` VARCHAR(50) COMMENT '用户姓名';
# 查询是否修改正确
SHOW CREATE TABLE `users`;
# (4)将users表的contact字段的类型由VARCHAR(100)改为VARCHAR(80)
ALTER TABLE `users` 
MODIFY COLUMN `contact` VARCHAR(80) COMMENT '用户联系方式';
# 查询是否修改正确
SHOW CREATE TABLE `users`;
# (5)将users表的createTime字段添加索引
ALTER TABLE `users` 
ADD INDEX `IDX_USERS_CREATETIME` (`createTime`) USING BTREE;
# 查询是否添加正确
SHOW CREATE TABLE `users`;

2.3 查询数据表

语法:

SHOW CREATE TABLE 数据表名称;

示例:

# 查询表结构
SHOW CREATE TABLE `users`;

2.4 删除数据表(任何删除操作均需谨慎,请勿删表跑路)

语法:

# 删除单个数据表
DROP TABLE 数据表名称1;
# 删除多个数据表
DROP TABLE 数据表1名称,数据表2名称,...,数据表n名称;

示例:

DROP TABLE `users`;

3 库相关

3.1 创建实例库

语法(常用字段):

CREATE DATABASE 实例库名称 
DEFAULT CHARACTER SET 字符集 
DEFAULT COLLATE 排序规则 

实例库名称为必填,字符集、排序规则为非必填

字符集、排序规则如果不设置,则会采取mysql配置文件(my.cnf/my.ini)中的设置;如果在mysql配置文件中也没有设置,则会采取mysql本身的默认设置(此设置根据mysql版本不同而所有差异,具体可以在mysql官方网站查询,但建议在建表语句或者配置文件二选一,这样更清晰)

示例:

创建一个名为lctest的数据库,要求字符集是utf8mb4、排序规则是utf8mb4_0900_ai_ci

CREATE DATABASE lctest 
DEFAULT CHARACTER SET utf8mb4 
DEFAULT COLLATE utf8mb4_0900_ai_ci;

验证:

Step1:看执行命令后能否得到Query OK的响应

Step2:查看数据库是否已创建

SHOW DATABASES;

3.1 修改实例库

修改数据库一般是修改字符集或排序规则,这个操作可能会影响数据的存储和检索,一般很少会用到,通常会在数据库创建时就定义好字符集和排序规则,因此,本文只列举相关语法

ALTER DATABASE 实例库名称 
DEFAULT CHARACTER SET 字符集 
DEFAULT COLLATE 排序规则 

3.3 查询实例库

语法及示例:

SHOW DATABASES;

3.4 删除实例库(任何删除操作均需谨慎,请勿删库跑路)

语法:

DROP DATABASE 实例库名称;

示例:

DROP DATABASE lctest;

验证:

Step1:看执行命令后能否得到Query OK的响应

Step2:查看数据库是否已经被删除

SHOW DATABASES;

4 用户相关

连接数据库,是进行一切数据库相关操作的前提,在数据库的连接命令中,除了数据库服务地址、端口号等信息之外,最关键的就是连接数据库的用户名和密码了,下面将介绍数据库用户相关的增删改查基础语法

4.1 创建用户

语法(常用字段):

CREATE USER '用户名'@'主机名' IDENTIFIED BY '密码';

(1)用户名和密码需妥善保存,且建议采用强密码,避免使用他人易猜测的密码

(2)主机名一般填ip或域名,相当于白名单,代表允许指定的主机连接到此mysql服务。如果需要任何主机都能有权限连接此mysql服务,则可以填写通配符(%)

示例:

# 创建一个名称为lc,密码为lclc_6688的用户
# 仅允许此用户通过数据库服务器本机(localhost)连接数据库
CREATE USER 'lc'@'localhost' IDENTIFIED BY 'lclc_6688';

验证:

Step1:看执行命令后能否得到Query OK的响应

Step2:看能否在数据库服务器本机使用此用户登录连接至数据库

4.2 修改用户

4.2.1 修改用户名、密码

# 使用root或其他管理账户登录连接mysql,然后执行以下命令
# 将用户名从lc改为llcc
RENAME USER 'lc'@'localhost' TO 'llcc'@'localhost';
# 将密码从lclc_6688改为llcc_6688
ALTER USER 'llcc'@'localhost' IDENTIFIED BY 'llcc_6688';

验证:

Step1:看执行命令后能否得到Query OK的响应

Step2:看能否在数据库服务器本机使用新的用户名和密码登录连接至数据库

4.2.2 修改用户权限

语法:

# 新增权限
GRANT 权限项 ON 数据库名.数据表名 TO '用户名'@'主机名';
# 删除权限
REVOKE 权限项 ON 数据库名.数据表名 FROM '用户名'@'主机名';

(1)权限项,包括CREATE(增)、DELETE(删)、UPDATE(改)、SELECT(查)等数据库操作权限,用ALL PRIVILEGES可表示所有权限

(2)数据库名,指的是mysql中的实例库名称,用*可表示所有库

(3)数据表名,指的是实例库对应的数据表名称,用*可表示所有表

(4)用户名,指的是数据库user用户名称

(5)主机名,即:对应user用户的白名单主机名

示例:

# 给llcc这个用户添加此mysql中的所有实例库、所有实例表的所有操作权限
GRANT ALL PRIVILEGES ON *.* TO 'llcc'@'localhost';
# 给llcc这个用户移除mysql中的所有实例库、所有实例表的删除权限
REVOKE DROP,DELETE ON *.* FROM 'llcc'@'localhost';
# 操作之后需要刷新权限,否则不能实时生效
FLUSH PRIVILEGES;

验证:

Step1:看执行命令后能否得到Query OK的响应

Step2:查看llcc用户权限项是否正确

SHOW GRANTS FOR 'llcc'@'localhost';

4.3 查询用户

mysql中的各用户信息也是数据,也会有数据表来进行存储

在mysql中,会有一个名为mysql的实例库,此实例库中有一个名为user的数据表,其存放的就是mysql中各用户信息的数据

# 使用root或其他管理账户登录连接mysql,然后执行以下命令
SELECT * FROM mysql.user;

4.4 删除用户(任何删除操作均需谨慎,请勿删用户跑路)

语法:

DROP USER '用户'@'主机名';

示例:

DROP USER 'llcc'@'localhost';

验证:

Step1:看执行命令后能否得到Query OK的响应

Step2:查询此用户是否还存在于mysql实例库的user表中

# 使用root或其他管理账户登录连接mysql,然后执行以下命令
SELECT * FROM mysql.user;

5 附页

5.1 mysql常用内置函数

函数名称函数标识描述
字符串函数CONCAT()连接字符串。
——SUBSTRING()提取子字符串。
——REPLACE()替换字符串中的某些字符。
——LOWER()转换为小写。
——UPPER()转换为大写。
——TRIM()去除字符串两端的空格。
——LPAD()左侧填充字符串。
——RPAD()右侧填充字符串。
数值函数ABS()返回绝对值。
——CEILING()返回不小于原数的最小整数。
——FLOOR()返回不大于原数的最大整数。
——ROUND()四舍五入数值。
——POW()求次幂。
——SQRT()计算平方根。
日期和时间函数NOW()返回当前日期和时间。
——CURDATE()返回当前日期。
——CURTIME()返回当前时间。
——DATEDIFF()计算两个日期的差值。
——DATE_ADD()添加日期和时间。
——DATE_SUB()减去日期和时间。
——DAY()从日期中提取天数。
——MONTH()从日期中提取月份。
——YEAR()从日期中提取年份。
聚合函数COUNT()计算数量。
——SUM()计算总和。
——AVG()计算平均值。
——MAX()返回最大值。
——MIN()返回最小值。
条件函数IF()条件表达式。
——CASE...END多条件表达式。
其他函数VERSION()返回MySQL版本。
——USER()返回当前用户名称。
——DATABASE()返回当前数据库名称。

5.2 mysql字段常用数据类型

类型名称类型标识描述/最大长度
数值类型TINYINT很小的整数(8位)
——SMALLINT小的整数(16位)
——MEDIUMINT中等大小的整数(24位)
——INT标准整数(32位)
——BIGINT大的整数(64位)
——FLOAT单精度浮点数
——DOUBLE双精度浮点数
——DECIMAL定点数,可指定小数位数(例如:DECIMAL(10, 2) 表示总共10位数字,其中2位为小数)
字符串类型CHAR固定长度字符串(0-255字符)
——VARCHAR可变长度字符串(0-65,535字符)
——TINYTEXT小文本(最大长度 255字节)
——TEXT文本(最大长度 65,535字节)
——MEDIUMTEXT中等大小文本(最大长度 16,777,215字节)
——LONGTEXT大文本(最大长度 4,294,967,295字节)
——BINARY固定长度二进制字符串
——VARBINARY可变长度二进制字符串
日期和时间类型DATE日期(格式:YYYY-MM-DD
——TIME时间(格式:HH:MM:SS
——DATETIME日期和时间(格式:YYYY-MM-DD HH:MM:SS
——TIMESTAMP时间戳(格式:YYYYMMDDHHMMSS
——YEAR年份(范围:19012155
JSON类型JSON存储JSON文档
枚举和集合类型ENUM字符串对象的枚举(例如:ENUM('value1', 'value2')
——SET字符串对象的集合(例如:SET('value1', 'value2')
空间数据类型GEOMETRY表示几何对象
——POINT表示点
——LINESTRING表示线
——POLYGON表示多边形
二进制数据类型TINYBLOB很小的二进制大对象
——BLOB二进制大对象
——MEDIUMBLOB中等大小的二进制大对象
——LONGBLOB很大的二进制大对象

5.3 mysql常用约束类型

约束类型描述
NOT NULL确保列不接受NULL值。
NULL允许列接受NULL值(默认)。
UNIQUE强制列的唯一性,不能有重复的值(除了NULL)。
PRIMARY KEY指定列(或列的组合)作为表的主键,唯一且非空。
FOREIGN KEY建立当前表和另一个表之间的链接,要求引用的数据必须在另一个表中存在。
AUTO_INCREMENT用于数值类型的列,自动为新记录生成唯一的递增值。
DEFAULT指定列的默认值,如果插入记录时未指定值,则使用默认值。
CHECK确保列的值满足某个条件(MySQL 8.0.16及以上版本支持)。
INDEX为列创建索引,提高查询效率(不是SQL标准的列约束,但广泛使用)。

5.4 mysql常用运算符

类型名称标识描述/用法
算术运算符+加法
——-减法
——*乘法
——/除法(返回小数结果)
——%取模(返回余数)
——//整除(返回整数结果)
比较运算符=等于(与 == 相同)
——==等于
——!=不等于(与 <> 相同)
——<>不等于
——>大于
——<小于
——>=大于等于
——<=小于等于
——BETWEEN在某个范围内
——IS NULL检查是否为 NULL
逻辑运算符NOT逻辑非
——AND逻辑与
——OR逻辑或
位运算符&位与
——^位异或
——~位取反
——<<左移位
——>>右移位
字符串连接CONCAT()连接字符串(或使用 + 运算符)
赋值运算符:=在存储过程中赋值
范围运算符IN检查值是否在指定范围内
模式匹配运算符LIKE模糊匹配
——REGEXP/RLIKE正则表达式匹配
安全的平等比较<=>安全的等于比较,考虑 NULL 值
其他运算符DIV整除(仅接受整数操作数)
——MOD取模(可接受浮点数操作数)

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/2092171.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

BUUCTF PWN wp--jarvisoj_level0

第一步 checksec &#xff0c;该题为64位。 分析一下二进制保护机制&#xff1a; Arch: amd64-64-little 这个字段表示二进制程序的架构是 64 位的小端序的 x86-64 架构。小端序意味着低位字节存储在内存中的低地址上&#xff0c;高位字节存储在高地址上。RELRO: No RELRO …

迁移学习之领域自适应(domain adaptation)

比如有一堆有标注的训练数据&#xff0c;这些数 据来自源领域&#xff0c;用这些数据训练出一个模型&#xff0c;这个模型可以用在不一样的领域。在训练的时 候&#xff0c;我们必须要对测试数据所在的目标领域有一些了解。 随着了解的程度不同&#xff0c;领域自适应的方法也不…

(C++ STL)vector类的简单模拟实现与源码展示

vector类的简单模拟实现 一、前言二、vector 的成员变量三、vector 部分函数实现size、capacityreserveresizeinsert 与注意事项erase构造、析构、赋值拷贝 四、vector 源代码 以下代码环境为 VS2022 C。 一、前言 vector类 本质上就是数据结构中的顺序表。(可参考&#xff1…

【最新华为OD机试E卷】boos的收入(100分)-多语言题解-(Python/C/JavaScript/Java/Cpp)

🍭 大家好这里是春秋招笔试突围 ,一枚热爱算法的程序员 ✨ 本系列打算持续跟新华为OD-E/D卷的三语言AC题解 💻 ACM金牌🏅️团队| 多次AK大厂笔试 | 编程一对一辅导 👏 感谢大家的订阅➕ 和 喜欢💗 🍿 最新华为OD机试D卷目录,全、新、准,题目覆盖率达 95% 以上,…

4.负载均衡

文章目录 1.多级部署2.实现请求计数器3.负载均衡3.1服务端负载均衡3.2客户端负载均衡3.3自定义负载均衡3.4负载均衡策略3.5 LoadBalance 原理 4.部署实现 大家好&#xff0c;我是晓星航。今天为大家带来的是 负载均衡 相关的讲解&#xff01;&#x1f600; 1.多级部署 复制一…

C语言 | Leetcode C语言题解之第378题有序矩阵中第K小的元素

题目&#xff1a; 题解&#xff1a; bool check(int **matrix, int mid, int k, int n) {int i n - 1;int j 0;int num 0;while (i > 0 && j < n) {if (matrix[i][j] < mid) {num i 1;j;} else {i--;}}return num > k; }int kthSmallest(int **matri…

面试题小总结

一、为什么要使用Redis&#xff1f; 因为它是内存数据库&#xff0c;运行速度快因为它的工作线程是单线程&#xff0c;具有串行化&#xff0c;原子性具有IO模型&#xff0c;天生支撑高并发是kv模型&#xff0c;v具有多个数据结构具有本地方法&#xff0c;可以计算数据移动是二…

Mac用户必备:轻松添加Git SSH密钥全攻略

最近新买了一台MacBook笔记本&#xff0c;然后安装了git&#xff0c;准备下载代码&#xff0c;正好遇到配置GitHub的ssh密钥&#xff0c;记录一下整个操作流程。 操作步骤 在Mac上添加Git SSH密钥的步骤如下&#xff1a; 检查是否已有SSH密钥&#xff1a; 打开终端&#xff0…

Nginx: https解决安全问题

https原理 1 &#xff09;http协议存在的问题 数据使用明文传输&#xff0c;可能被黑客窃取 (需要信息加密)报文的完整性无法验证&#xff0c;可能被黑客篡改 (需要完整性校验)无法验证通信双方的身份&#xff0c;可能被黑客伪装 (需要身份认证) 2 ) https 原理 所谓 https,…

新160个crackme - 043-riijj_cm_20041121

运行分析 除了主程序还有一个dll文件&#xff0c;应该是要加载pf1.dll这个动态链接库运行主程序&#xff0c;需破解Name和Serial&#xff0c;点击注册无反应 PE分析 C程序&#xff0c;32位&#xff0c;无壳 静态分析&动态调试 尝试ida动调加载动态链接库pf1.dll&#xff0c…

全能型AI“草莓”:未来趋势还是市场泡沫?

你好&#xff0c;我是三桥君 近日&#xff0c;OpenAI宣布将在秋季推出代号为“草莓”的新AI模型。这一消息迅速引起了科技界和市场的广泛关注。 OpenAI的新项目“草莓”&#xff08;Strawberry&#xff09;是一个备受关注的人工智能模型&#xff0c;预计将在今年秋季发布。这个…

算法复盘——LeetCode hot100:哈希

文章目录 哈希表哈希表的基本概念哈希表的使用1. 插入操作2. 查找操作3. 删除操作 哈希表的优点和缺点1.两数之和复盘 242.有效的字母异位词复盘 49.字母异位词分组复盘 128. 最长连续序列复盘HashSet 哈希表 先来搞清楚什么是哈希表吧~ 概念不清楚方法不清楚怎么做题捏 哈希表…

MongonDB-索引

一、索引-index (一) 概述 索引支持在MongoDB中高效地执行查询。如果没有索引&#xff0c;MongoDB必须执行全集合扫描&#xff0c;即扫描集合中的每个文档&#xff0c;以选择与查询语句匹配的文档。这种扫描全集合的查询效率是非常低的&#xff0c;特别在处理大量的数据时&am…

firewalld 防火墙常用命令,新手必看

firewalld 防火墙常用命令 防火墙状态命令 systemctl start firewalld #启动防火墙 systemctl stop firewalld #关闭防火墙 systemctl restart firewalld #重启防火墙 systemctl enable firewalld #设置开机自启 systemctl disable firewalld #禁用开机自启 systemctl s…

自己开发完整项目一、登录功能-03(使用springSecurity安全框架,查询用户角色权限)

一、说明 在前面两章节&#xff0c;实现了通过springsecurity来进行用的登录认证&#xff0c;当用户输入用户名和密码之后&#xff0c;通过额数据库中的信息比对&#xff0c;比对成功那么放行。但是还存在一个问题&#xff1a;因为系统的所有页面包括按钮都是有各自的权限&…

全网最全robotframework自动化测试环境搭建

一、前言 1、在2019年之前&#xff0c;robotframework-ride的版本一直是1.5.2.1&#xff0c;是2016年1月份的版本&#xff0c;只能安装在python2.7的环境上&#xff0c;导致如果想同时使用robotframework做测试且又需要python3环境编写python代码的小伙伴都需要在操作系统上安…

Golang 读取文件

GoLang读取文件需要用到os类去打开文件&#xff0c;然后再用其他方式分析文件里的内容。打开文件比较简单&#xff0c;使用os.Open就可以了&#xff0c;记住用defer关闭就行。但是读取文件内容就头疼了&#xff0c;以文本文件为例子&#xff0c;就有各种方式 读取到byte数组 首…

渐进式衰老?医美三剑客的“市梦率”幻灭了

医美股神话彻底幻灭了。 从股价蒸发到业绩失速&#xff0c;“医美三剑客”上演着繁华落幕&#xff0c;回归平凡的剧本。 近一年来&#xff0c;爱美客、华熙生物、昊海生科股价分别累计下跌52.97%、46.03%、16.09%。 “医美三剑客”近一年累计跌幅&#xff08;资料来源&#x…

分水岭算法简介

分水岭算法是一种经典的图像分割技术&#xff0c;广泛应用于图像处理领域。它的名称源自地理学中的“分水岭”概念&#xff0c;即在地形中&#xff0c;水从高处流向低处&#xff0c;最终汇聚成河流的过程。在图像分割中&#xff0c;分水岭算法将灰度图像视为地形&#xff0c;将…

STM32(八):定时器——输入捕获实验

目录 输入捕获模式测频率&#xff1a; 结构图&#xff1a; 步骤&#xff1a; 部分函数详解&#xff1a; 源码&#xff1a; PWMI模式测频率占空比&#xff1a; 结构图&#xff1a; ​编辑 举例说明 源码&#xff1a; 输入捕获模式测频率&#xff1a; 结构图&#xf…