欢迎光临
我们一直在努力

MySQL 完整学习总结

MySQL
开源关系型数据库(RDBMS),采用 C/S 架构;数据存储在二维表,支持 SQL 结构化查询语言。

  • 核心组成 数据库(database):多个数据表集合
    数据表(table):行(记录)+ 列(字段)
    字段(column):列,定义数据类型、约束
    记录(row):一行完整数据
    约束:限制字段数据规则
    索引:提升查询速度
    存储引擎:决定表如何存储、读写数据(表级别设置)
  • SQL 四大分类 DDL 数据定义语言:库、表结构
    CREATE / ALTER / DROP / TRUNCATE DML
    数据操作语言:操作表里数据
    INSERT / UPDATE / DELETE / SELECT DCL
    数据控制语言:权限管理 GRANT / REVOKE
    TCL 事务控制语言:COMMIT / ROLLBACK / SAVEPOINT
  • 二、MySQL 数据类型

    类型占用字节范围场景
    TINYINT 1 -128~127;无符号 0~255 状态、布尔标记(0/1)
    SMALLINT 2 ±32767 少量数字编码
    INT 4 ±21 亿 最常用 id、编号
    BIGINT 8 超大整数 雪花 ID、海量数据表主键
    FLOAT 4 单精度浮点 不推荐存储金额(精度丢失)
    DOUBLE 8 双精度浮点 依旧不适合金额
    DECIMAL(M,D) 可变 定点小数 金额、财务数据首选

    二进制浮点无法精确表示小数;必须 DECIMAL(总长度,小数位数)

    2. 字符串类型

    类型特点场景
    CHAR(n) 固定长度,不足自动补空格;查询速度快 固定长度:手机号、身份证
    VARCHAR(n) 可变长度,占用空间更小;n 代表最大字符数 绝大多数短文本:名称、地址
    TEXT 大文本,无默认索引 文章内容、长备注(禁止做主键索引)
    BLOB 二进制字节 图片、文件二进制(不推荐,文件存 oss,数据库存地址)

    MySQL5.7 中 varchar 最大 65535 字节,utf8 一个字符占 3 字节,不是随便写 n=10000

    3.日期时间类型
    DATE 3 字节:yyyy-MM-dd 只存日期
    TIME 3 字节:HH:mm:ss 时间
    DATETIME 8 字节:日期 + 时间,不受时区影响
    TIMESTAMP 4 字节:时间戳,自动转时区;范围较小(1970~2038)【2038 时间炸弹】

    新项目优先 DATETIME,避开 timestamp2038 上限
    自动更新时间:update_time DATETIME ON UPDATE CURRENT_TIMESTAMP
    4. 枚举 & 集合
    ENUM (’ 男 ‘,’ 女 '):单选
    SET (‘a’,‘b’):多选,极少使用

    三、字段约束(建表必备)
    PRIMARY KEY 主键:唯一 + 非空,一张表只能一个主键(可以联合主键)
    UNIQUE 唯一约束:值不能重复,允许一个 null
    NOT NULL 非空
    DEFAULT 默认值
    AUTO_INCREMENT 自增(仅整数主键)
    FOREIGN KEY 外键:维护表与表关系

    生产建议:InnoDB 虽然支持外键,但互联网项目大多禁用外键。
    外键会降低并发性能,死锁风险提升,业务代码手动控制关联完整性

    四、DDL 库、表实操命令

    — 创建数据库
    CREATE DATABASE IF NOT EXISTS test DEFAULT CHARACTER SET utf8mb4;
    — utf8mb4 完整utf8,支持emoji;普通utf8不支持表情

    — 创建表示例
    CREATE TABLE `user`(
    id BIGINT PRIMARY KEY AUTO_INCREMENT COMMENT '主键id',
    username VARCHAR(50) NOT NULL COMMENT '用户名',
    phone CHAR(11) UNIQUE COMMENT '手机号',
    money DECIMAL(12,2) DEFAULT 0 COMMENT '余额',
    create_time DATETIME DEFAULT CURRENT_TIMESTAMP
    )ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COMMENT='用户表';

    — 修改表
    ALTER TABLE user ADD age TINYINT;
    ALTER TABLE user MODIFY username VARCHAR(80);
    ALTER TABLE user DROP COLUMN age;

    — 删除
    DROP TABLE IF EXISTS user;
    TRUNCATE TABLE user; — 清空表数据,重置自增;DDL语句,无法回滚

    DELETE:DML,逐行删除,可以事务回滚,不会重置自增
    TRUNCATE:DDL,销毁重建表,速度极快,不能回滚

    五、DML 增删改查

    –插入
    INSERT INTO user(username,phone) VALUES('张','13800138000');
    –查询
    SELECT id,username FROM user WHERE id=1;
    –修改(必须加WHERE,不然会全表更新)
    UPDATE user SET money=100 WHERE id=1;
    –删除
    DELETE FROM user WHERE id=1;

    查询

    –条件、模糊查询
    SELECT * FROM user WHERE username LIKE '张%';
    –分页 LIMIT offset,size
    SELECT * FROM user LIMIT 0,10;

    –聚合函数:COUNT SUM MAX MIN AVG
    –COUNT(*) 统计所有行;COUNT(字段)忽略NULL值
    SELECT COUNT(*) FROM user;

    –分组 GROUP BY + HAVING
    –WHERE过滤原始数据,HAVING过滤分组后的结果
    SELECT age,COUNT(*) FROM user GROUP BY age HAVING COUNT(*)>2;

    –多表连接【重】
    –INNER JOIN 内连接:两边匹配的数据才出现
    –LEFT JOIN 左连接:左表全部保留,右表匹配不到填充null
    –RIGHT JOIN 右连接
    SELECT u.username,o.order_id
    FROM `user` u
    LEFT JOIN `order` o ON u.id=o.user_id;

    六、存储引擎

    执行 SHOW ENGINES; 查看支持引擎

  • InnoDB(MySQL5.5 + 默认)【聚簇索引】
    支持:事务、行锁、外键、崩溃安全恢复、聚簇索引
    适用:绝大多数业务表
  • MyISAM【非聚簇索引】
    不支持事务、不支持行锁;只有表锁
    优势:查询速度快,占用空间小
    缺陷:崩溃容易丢数据;并发写入极差
    场景:静态历史报表
  • 七、索引
    一种有序数据结构(InnoDB 默认 B + 树),相当于书籍目录,加速查询;

    代价:占用磁盘、降低插入 / 更新 / 删除速度(需要维护索引)。

    InnoDB B + 树索引原理
    B + 树:只有叶子节点存储真实行数据;非叶子节点只存索引键,用于路由
    所有叶子节点通过双向链表相连,**范围查询(> < between、like 前缀匹配)**效率极高
    对比 B 树:B 树每个节点都带数据,IO 次数更多
    索引分类

  • 主键索引(聚簇索引)
    InnoDB 每张表必须有聚簇索引
    如果没有主键 → 找唯一非空索引;都没有自动生成隐藏 rowid
    聚簇索引叶子节点 = 完整一行数据
  • 二级索引存储的不是完整数据,存主键值
    . 回表查询:通过二级索引拿到主键,再去聚簇索引查找完整数据(性能损耗)

  • 二级索引(普通索引、唯一索引)
    叶子节点:索引值 + 主键 id
  • 联合索引(复合索引)
    INDEX idx_a_b(a,b)
    最左匹配原则
    建立索引 (a,b,c)
    有效条件:查询条件必须从最左列开始连续匹配
  • –生效
    where a=?
    where a=? and b=?
    where a=? and b=? and c=?
    –失效,跳过最左a
    where b=?
    where b=? and c=?

    范围条件后面的索引失效 where a=1 and b>10 and c=99 b 是范围,c 字段索引不生效

  • 覆盖索引
    查询字段全部在索引里,不需要回表,性能最优
  • 例:索引 idx_name_phone (name,phone) select name,phone from user where
    name=‘张’ → 覆盖索引

    索引失效场景
    1.字段上使用函数:
    WHERE YEAR(create_time)=2026
    2.隐式类型转换:字符串 varchar 字段使用数字查询 where phone=138000
    3.使用 != <> NOT IN IS NOT NULL(大部分情况失效)
    4.like、 %关键词 、通配符放前面
    5.or 左右字段没有同时建立索引
    6.违反最左匹配原则

    看字段: type:性能等级 system > const > eq_ref > ref > range > index > ALL ALL
    代表全表扫描,必须优化 key:实际使用索引 Extra:Using filesort(文件排序,无索引排序)、Using
    temporary(临时表,严重损耗)

    八、事务 Transaction
    一组 SQL 语句,要么全部执行成功,要么全部失败回滚,保证业务原子性(转账:A 扣钱,B 加钱必须同时成功)
    2. ACID 四大特性

  • 原子性 Atomic:不可分割,全成功 / 全失败(undo 日志实现)
    2.一致性 Consistency:事务前后数据合法(约束不破坏)
  • 隔离性 Isolation:多个事务之间互不干扰(锁 + MVCC 实现,最难!)
  • 持久性 Durability:提交后数据永久保存,宕机不丢失(redo 日志)
  • 事务隔离级别
    并发事务会出现三类问题:
    脏读:读到其他事务未提交的数据
    不可重复读:同一事务内,两次读取同一数据,中间被别的事务修改提交,结果不一致
    幻读:同一范围查询,别的事务插入新数据,再次查询多出数据
  • 隔离级别脏读不可重复读幻读InnoDB 默认级别
    读未提交 READ UNCOMMITTED 允许 允许 允许 不用
    读已提交 READ COMMITTED (RC) 禁止 允许 允许 Oracle 默认
    可重复读 REPEATABLE READ (RR) 禁止 禁止 大部分情况禁止 MySQL InnoDB【默认】
    串行化 SERIALIZABLE 禁止 禁止 禁止 并发极低,极少使用
  • MVCC 多版本并发控制(RR 隔离底层原理)
    MVCC = 不加锁实现读操作并发(快照读)
  • 核心:undo 日志(数据历史版本)+ 行隐藏字段(trx_id,roll_pointer)+ Read View

    两种读:
    快照读(普通 select):走 MVCC,读取历史快照,不加行锁
    当前读(select … for update /update/delete):读取最新数据,加行锁

    RR 级别下 MVCC 机制解决幻读;仅快照读生效;当前读依旧存在幻读问题,InnoDB 依靠Gap Lock 间隙锁解决幻读

    九、InnoDB 锁机制
    锁分类

  • 按粒度
    表锁:锁住整张表;MyISAM 只有表锁;开销小,并发差
    行锁(Record Lock):InnoDB;只锁定匹配的行;并发高;仅索引生效时才会走行锁!
    致命坑:如果查询条件没有索引,行锁会升级为表锁!
  • 锁模式
    共享锁 S(读锁):多个事务可以同时加 S 锁
    排他锁 X(写锁):只能一个事务持有
  • 间隙锁
    Gap Lock + 临键锁 Next-Key Lock【RR 独有,解决幻读】
    锁定索引间隙,阻止其他事务插入数据;
  • RC 隔离级别没有间隙锁 间隙锁会带来死锁风险

    死锁
    多个事务互相持有对方需要的锁,无限等待
    触发条件:事务获取锁顺序不一致 + 行锁 + 间隙锁
    排查:SHOW ENGINE INNODB STATUS;
    规避方案:统一所有事务加锁顺序,缩短事务执行时间

    十、三大日志(底层原理)
    redo log(重做日志):崩溃恢复,保证持久性。先写日志,再刷磁盘(WAL 预写日志机制)
    undo log(回滚日志):事务回滚、MVCC 历史数据版本
    binlog(二进制日志):服务层日志,记录所有修改数据 SQL;用于主从复制、数据恢复
    redo 属于 InnoDB 引擎层;binlog 属于 MySQL 服务层
    WAL 机制(Write Ahead Log)
    修改数据不立刻刷新磁盘页,先写入 redo log;提升性能,防止宕机丢失数据

    拓展进阶方向(后续深入)
    主从复制、读写分离、分库分表、慢查询日志调优、MySQL 监控、缓存与数据库一致性

    General SQL Optimization Solutions
    1.禁止 SELECT *,只查询需要字段,减少网络 + 内存消耗;
    2. 避免大事务,拆分长事务(减少锁持有时间,降低死锁);
    3.分页深度优化:limit 100000,10 极慢,改用主键过滤 where id>100000 limit 10
    4. 大表不要使用 JOIN 超大关联,考虑业务拆分 ;
    5.控制单表数据量,建议千万级别考虑分库分表;
    6.合理选择字符集 utf8mb4;

    赞(0)
    未经允许不得转载:171主机测评 » MySQL 完整学习总结
    分享到: 更多 (0)

    评论 抢沙发

    • 昵称 (必填)
    • 邮箱 (必填)
    • 网址