1.初识Mysql
JavaEE:企业级Java开发 Web
前端(页面:展示,数据!)
后台(连接点:连接数据库JDBC,链接前端:控制,控制试图跳转,和给前端传递数据)
数据库(村数据,Txt,Excel,Word)
操作系统,数据结构与算法!当一个不错的程序猿
离散数学,数学电路,体系结构,编译原理,+实战经验
1.1什么是数据库
数据库(DB,DataBase)
概念:数据仓库,软件,安装在操作系统(Windows,linux,mac,…)之上!SQL,可以存储大量的数据,500万
作用:存储数据,管理数据
1.3数据库分类
关系型数据库:Excel
- Mysql,Oracle,Sql Server,DB2,SQLIite
- 通过表和表之间,行和列之间的关系进行数据的存储,学院信息表,考勤表
非关系型数据库:(NoSQL)Not Only
- Redis、MongDB
- 非关系型数据库,对象存储,通过对象的自身的属性来决定
DBMS(数据库管理系统)
- 数据库的管理软件,科学有效的管理我们的数据,维护和获取数据
- Mysql,数据库管理系统!
1.4Mysql简介
官网下载地址:https://dev.mysql.com/downloads/mysql/
安装建议:
5.7稳
5.8要加时区
1.尽量不要使用exe,注册表
2.尽可能使用压缩包安装
Mysql安装
1.下载进去官网
安装
- 解压
- 将解压文件放到自己的环境目录下
- 配置环境变量
- 新建mysql配置文件my.ini文件
[mysqld]
#目录要自己的目录
basedir=D:\Work\mysql-5.7.19-winx64\
datadir=D:\Work\mysql-5.7.19-winx64\data\
port=3306
skip-grant-tables
记得改了密码之后注释掉#skip-grant-tables
5. 启动管理员模式下的cmd,运行所有的命令–在开始中搜索找到命令提示符
navicat下载安装
https://www.jianshu.com/p/2494e02caf63
1.6连接数据库
命令行链接
mysql -u root -p123456 #登录mysql
update mysql.user set authentication_string=("123456") where user="root"; #修改用户密码
select host,user,authentication_string from mysql.user;#查找用户没密码
flush privileges; #刷新缓存
exit;退出连接
---------------------
show databases;# 显示数据库列表
use mysql;//打开库
show tables;#显示表
describe 表名;#显示数据表的结构
create database 库名;#建库
数据库语言
DDL 定义
DML 操作
DQL 查询
DCL 控制
2.操作数据库(了解)
操作数据库>操作数据库中的表>操作数据库中的表的数据
- 创建数据库
REATE DATABASE IF NOT EXISTS test;
- 删除数据库
DROP DATABASE IF EXISTS test;#IF EXISTS可省略
- 使用数据库
--tab 键的上面,如果你的表明或者字段名是一个特殊字符,就需要带''
use test;
use 'test';
- 查看数据库
SHOW DATABASES;
2.2数据库的列类型
数值
- tinyint 十分小的数据 1个字节
- smallint 较小的数据 2个字节
- mediumint 中等大小的数据 3个字节
- int 标准的整数 4个字节 常用的 int
- bigint 较大的数据 8个字节
- float 浮点数 4个字节
- double 浮点数 8个字节(精度问题)
- decimal 字符串形式的浮点数 金融计算的时候,一般使用decimal
字符串
- char 字符串固定的大小 0~255
- vachar 可变字符串 0~65535 常用的 String
- tinytext 微型文本 2^8-1
- text 文本串 2^16-1
时间日期
java.until.Date
- date YYYY-MM-DD,日期格式
- time HH:mm:ss 时间格式
- datetime YYYY-MM-DD HH:mm:ss 最常用的时间格式
- timestamp 时间戳 1970.1.1到现在的毫秒数! 也较为常用
- year 年份表示
null
没有值:未知
注意,不要使用NULL进行运算,结果为null
2.3数据库的字段属性
- 启动管理员模式下的cmd,运行所有的命令–在开始中搜索找到命令提示符
所有的创建和删除操作尽量加上判断,以免出错
建议写小写,mysql大小写不敏感
3Mysql 数据管理
3.1外键(了解)
外键不建议使用,删除都不好删除
最佳实践
- 数据库就是单纯的表,只用来存储数据,只有行行(数据)和列(字段)
- 我们想使用多张表的数据,想使用外键(程序去实现)
3.2DDL
insert
update
delete
3.3 添加
修改
删除
了解即可:Delete删除的问题,重启数据库,现象
- innoDB 自增列会从1开始(存在内存当中,断电即失)
- MyISAM继续从上一个子增量开始(存在文件中的,不会丢失)
4.DQL查询数据(最重点)
4.1DQL
4.2指定查询字段
4.3where条件子句
联表查询
自连接
4.5分页排序
4.6子查询和嵌套查询
4.7分组过滤
5.2聚合函数
5.3数据库级别的MD5加密(扩展)
6.事务
6.1什么是事务
执行事务
模拟场景
7.索引
7.2测试索引
DELIMITER $$ --写函数之前必须写,标志
CREATE FUNCTION mock_data () RETURNS INT BEGIN
DECLARE
num INT DEFAULT 1000000;
DECLARE
i INT DEFAULT 0;
WHILE
i < num DO
INSERT INTO app_user ( name, email, phone, gender, password, age )
VALUES
(
CONCAT( '用户', i ),
'277253309@qq.com',
CONCAT(
'18',
FLOOR(
RAND()*((
9999999999-1000000000
)+ 100000000
))),
FLOOR( RAND()* 2 ),
UUID(),
FLOOR( RAND()* 100 ));
SET i = i + 1;
END WHILE;
RETURN i;
END;
查询测试
没有索引:SELECT * FROM app_user WHERE name=‘用户10000’;–时间: 0.366s
EXPLAIN SELECT * FROM app_user WHERE name=‘用户10000’;–查找了99万多条数据
建立索引
–id_表名_字段名
– CREATE INDEX 索引名 on 表(字段)
CREATE INDEX id_app_user_name ON app_user(NAME);SELECT * FROM app_user WHERE name=‘用户10000’;–时间: 0.012s
索引在小数据量的时候,用处不大,但是在大数据的时候,区别十分明显
7.3索引原则
- 索引并不是越多越好
- 不要在经常变动数据加索引
- 小数据量的表不需要加索引
- 索引一般加在常用来查询的字段上!
索引的数据结构
Hash类型的索引
Btree:InnoDB的默认数据结构
来来来!阅读这篇文章
mysql索引背后的数据结构和算法原理
索引有几种算法:Hash算法、平衡二叉树,数据结构B树,数据结构B+树
Hash索引:
优点:通过字段的值计算的hash值,定位数据非常快
缺点:不支持范围查询
为什么不支持范围查询?
因为底层数据结构是散列的,无法比较大小
可视化工具大集合:https://www.cs.usfca.edu/~galles/visualization/Algorithms.html
平衡二叉树索引:
平衡二叉树 会取中间值,中间值左边称为左子树,中间值右边称为右子树,左边小于中间值,右边大于中间值,可以通过AVL Tree工具演示查看https://www.cs.usfca.edu/~galles/visualization/AVLtree.html
优点:平衡二叉树算法基本与二叉树查询相同,效率比较高(二分法查询)
缺点:插入操作需要旋转,支持范围查询(范围查询效率不高,要回旋,还要比较上面的数字)
平衡二叉树磁盘IO性质
4次IO操作
平衡二叉树 查询效率还可以,缺点:虽然支持范围查询,但是回旋查询效率低
规律:如果树的高度越高,那么查询10次数越多
如何去减少查询10次数?
B树在平衡二叉树中,减少树的高度
数据结构B树:
B-Tree可视化工具https://www.cs.usfca.edu/~galles/visualization/BTree.html
结论:B树比平衡二叉树减少了一次IO操作,(越多减少次数越多)
B树在平衡二叉树基础上改进的,也能支持范围查询,B树比平衡二叉树效率要高,
因为B树的节点中可以两个元素,从而减少树的高度,从而提高查询效率,范围查询还是比较低
数据结构B+树:
可视化工具:https://www.cs.usfca.edu/~galles/visualization/BPlusTree.html
B+树:解决范围查询问题,减少IO查询的操作。
B+树相比B树,新增叶子节点与非叶子节点关系,叶子节点中包含了key和value,非叶子节点中只是包含了key,不包含value。
B+树算法:通过继承了B树的特征,B+树相比B树,新增叶子节点与非叶子节点关系,叶子节点中包含了key和value,非叶子节点中只是包含了key,不包含value。通过非叶子节点查询叶子节点获取对应的value。所有相邻的叶子节点包含飞叶子节点,使用链表进行结合,有一定顺序排序,从而范围查询效率非常高。
缺点:因为有冗余的节点数据,会比较占硬盘大小。
叶子节点:key和value
非叶子节点:只有key
7.4MyISAM和InnoDB 引擎索引B+树区别
MyISAM和InnoDB都是采用B+树进行实现
MyISAM使用叶子节点的value存放地址,再通过地址对应查询行树。
InnoDB使用叶子节点value行的数据(它是将行里面的数据放在value中,相对占用内存硬盘大小),个人觉得InnoDB更好,占硬盘,提高了效率
Mysql索引数据结构 写的也挺好的
一颗B+树上能存多少数据 2000万
8权限管理和数据库备份
8.1用户管理
- 操作数据库mysql中的user表
视图化操作-方法2
8.2备份
-
navicat导出表数据和结构(略)
-
使用命令行导出 使用mysqldump命令
假设你要备份数据库,防止数据丢失
9数据库的归类,三大范式
10JDBC(重点)
10.1数据库驱动
驱动:声卡,显卡,数据库
我们的程序会通过数据库 驱动和数据库打交道
10.2 JDBC
java.sql
javax.sql
还需要导入一个数据库驱动包mysql-connector-java-5.1.47.jar
10.3第一个JDBC程序
创建测试数据库
创建一个普通项目
导入数据库目录
package com.ljh.lesson01;
import java.sql.*;
//我的第一个Jdbc程序
public class JdbcFirstDemo {
public static void main(String[] args) throws ClassNotFoundException, SQLException {
//1.加载驱动
Class.forName("com.mysql.jdbc.Driver");//固定写法,加载驱动
//2.用户信息和url
String url = "jdbc:mysql://localhost:3306/test?useUnicode=true&characterEncoding=utf8&useSSL=true";
String username="root";
String password="123456";
//3.连接成功,数据库对象
Connection connection = DriverManager.getConnection(url, username, password);
//4.执行sql的对象 Statement 执行SQL的对象
Statement statement = connection.createStatement();
//5.执行SQL的对象 去执行SQL,可能存在结果,查看返回结果
String sql = "select * from users";
ResultSet resultSet = statement.executeQuery(sql);
while (resultSet.next()){
System.out.println("id=" + resultSet.getObject("id"));
System.out.println("name=" + resultSet.getObject("name"));
System.out.println("password=" + resultSet.getObject("password"));
System.out.println("======================");
}
//6.释放连接
resultSet.close();
statement.close();
connection.close();
}
}
id=1
name=li
password=123456
======================
id=2
name=zhang
password=123456
======================
id=3
name=zeng
password=123456
======================
id=4
name=luo
password=123
======================
步骤总结:
- 加载驱动
- 连接数据库DriverManager
- 获取执行sql的对象Statement
- 获取返回的结果集
- 释放连接
10.4statement对象
jdbc连接等操作集中为工具类
package com.ljh.lesson02.util;
import java.io.IOException;
import java.io.InputStream;
import java.sql.*;
import java.util.Properties;
public class JdbcUtils {
private static String driver = null;
private static String url = null;
private static String name = null;
private static String password = null;
static {
try{
InputStream in = JdbcUtils.class.getClassLoader().getResourceAsStream("db.properties");
Properties properties = new Properties();
properties.load(in);
driver=properties.getProperty("driver");
url=properties.getProperty("url");
name=properties.getProperty("name");
password=properties.getProperty("password");
//1.驱动只用加载一次
Class.forName(driver);
} catch (Exception e) {
e.printStackTrace();
}
}
//获取连接
public static Connection getConnection() throws SQLException {
return DriverManager.getConnection(url,name,password);
}
//释放连接资源
public static void release(Connection conn, Statement st, ResultSet rs){
if(rs != null){
try {
rs.close();
} catch (SQLException e) {
e.printStackTrace();
}
}
if(conn != null){
try {
conn.close();
} catch (SQLException e) {
e.printStackTrace();
}
}
if(st != null){
try {
st.close();
} catch (SQLException e) {
e.printStackTrace();
}
}
}
}
//插入语句
package com.ljh.lesson02;
import com.ljh.lesson02.util.JdbcUtils;
import java.sql.Connection;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.sql.Statement;
public class TestInsert {
public static void main(String[] args) throws SQLException {
Connection conn = null;
Statement st = null;
ResultSet res = null;
try {
conn = JdbcUtils.getConnection();//获取数据库连接
st = conn.createStatement();//获取sql的执行对象
String sql = "INSERT into users (`name`,`password`) VALUES ('he','123456')";
int i = st.executeUpdate(sql);
if(i>0){
System.out.println("更新成功");
}
} catch (SQLException e) {
e.printStackTrace();
}finally {
JdbcUtils.release(conn,st,res);
}
}
}
sql注入
package com.ljh.lesson02;
import com.ljh.lesson02.util.JdbcUtils;
import java.sql.Connection;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.sql.Statement;
public class SQL注入 {
public static void main(String[] args) {
//这里sql拼接
login("' or '1=1","' or '1=1");
}
public static void login(String username,String password){
Connection conn = null;
Statement st = null;
ResultSet res = null;
try {
conn = JdbcUtils.getConnection();//获取数据库连接
st = conn.createStatement();//获取sql的执行对象
//select * from users where `name` = 'li' and `password` = '123456'
String sql = "select * from users where `name` ='"+username+"' and 'password'='"+password+"'";
System.out.println(sql);
res= st.executeQuery(sql);
while(res.next()){
System.out.println(res.getObject("name"));
}
} catch (SQLException e) {
e.printStackTrace();
}finally {
JdbcUtils.release(conn,st,res);
}
}
}
10.5 PreparedStatement对象
PreparedStatement可以防止sql注入,效率更好
package com.ljh.lesson03;
import com.ljh.lesson02.util.JdbcUtils;
import java.sql.*;
public class TestInsert {
public static void main(String[] args) {
Connection conn = null;
PreparedStatement st = null;
ResultSet res = null;
try {
conn = JdbcUtils.getConnection();//获取数据库连接
//select * from users where `name` = 'li' and `password` = '123456'
String sql = "select * from users where `name` = ? and `password` = ?";
st = conn.prepareStatement(sql);//预编译sql,先写sql,然后不执行
//手动给参赋值
st.setString(1,"li");
st.setString(2,"123456");
//执行cha
res = st.executeQuery();
while(res.next()){
System.out.println(res.getObject("name"));
}
} catch (SQLException e) {
e.printStackTrace();
}finally {
JdbcUtils.release(conn,st,res);
}
}
}
Idea连接数据库
如果发现没有驱动文件,点击左上角扳手图标,
导入我们之前的5.7的驱动jar包
10.8事务
package com.ljh.lesson04;
import com.ljh.lesson02.util.JdbcUtils;
import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;
public class TestTransaction1 {
public static void main(String[] args) {
Connection conn = null;
PreparedStatement st = null;
ResultSet res = null;
try {
conn = JdbcUtils.getConnection();//获取数据库连接
//关闭数据库的自动提交,自动会开启事务
conn.setAutoCommit(false);//开启事务
String sql1 = "update account set money = money-100 where name='A";
st = conn.prepareStatement(sql1);
st.executeUpdate();
String sql2 = "update account set money = money+100 where name='B";
st = conn.prepareStatement(sql2);
st.executeUpdate();
//业务完毕,提交事务
conn.commit();
System.out.println("成功!");
} catch (SQLException e) {
try {
conn.rollback();
} catch (SQLException ex) {
ex.printStackTrace();
}
e.printStackTrace();
}finally {
JdbcUtils.release(conn,st,res);
}
}
}
10.9、数据库连接池
数据库连接—执行完毕–释放
连接–释放 十分浪费系统资源
池化技术:准备一些预先的资源,过来就连接预先准备好的
–开门–业务员:等待–服务–
常用连接数 10个
最小连接数:10(这不是一定的)
最大连接数:业务最高承载上限
等待超时:100ms
编写连接池,实现一个接口 DataSource
开源数据实现(拿来即用)
DBCP
C3P0
Druid:阿里巴巴
使用了这些数据库连接池之后,我们的项目开发中就不需要编写连接数据库的代码了!
DBCP
需要用到的jar包
commons-dbcp-1.4.jar、commons-pool-1.6.jar
#连接设置
driverClassName=com.mysql.jdbc.Driver
url=jdbc:mysql://localhost:3306/test?useUnicode=true&characterEncoding=utf8&useSSL=true
username=root
password=123456
#<!-- 初始化连接 -->
initialSize=10
#最大连接数量
maxActive=50
#<!-- 最大空闲连接 -->
maxIdle=20
#<!-- 最小空闲连接 -->
minIdle=5
#<!-- 超时等待时间以毫秒为单位 6000毫秒/1000等于60秒 -->
maxWait=60000
#JDBC驱动建立连接时附带的连接属性属性的格式必须为这样:[属性名=property;]
#注意:"user" 与 "password" 两个属性会被明确地传递,因此这里不需要包含他们。
connectionProperties=useUnicode=true;characterEncoding=gbk
#指定由连接池所创建的连接的自动提交(auto-commit)状态。
defaultAutoCommit=true
#driver default 指定由连接池所创建的连接的只读(read-only)状态。
#如果没有设置该值,则“setReadOnly”方法将不被调用。(某些驱动并不支持只读模式,如:Informix)
defaultReadOnly=
#driver default 指定由连接池所创建的连接的事务级别(TransactionIsolation)。
#可用值为下列之一:(详情可见javadoc。)NONE,READ_UNCOMMITTED, READ_COMMITTED, REPEATABLE_READ, SERIALIZABLE
defaultTransactionIsolation=READ_UNCOMMITTED
package com.ljh.lesson05.utils;
import org.apache.commons.dbcp.BasicDataSourceFactory;
import javax.sql.DataSource;
import java.io.InputStream;
import java.sql.*;
import java.util.Properties;
public class JdbcUtils_DBCP {
private static DataSource dataSource= null;
static {
try{
InputStream in = JdbcUtils_DBCP.class.getClassLoader().getResourceAsStream("dbcpconfig.properties");
Properties properties = new Properties();
properties.load(in);
//创建数据源 工厂模式-->创建
dataSource = BasicDataSourceFactory.createDataSource(properties);
} catch (Exception e) {
e.printStackTrace();
}
}
//获取连接
public static Connection getConnection() throws SQLException {
return dataSource.getConnection();
}
//释放连接资源
public static void release(Connection conn, Statement st, ResultSet rs){
if(rs != null){
try {
rs.close();
} catch (SQLException e) {
e.printStackTrace();
}
}
if(conn != null){
try {
conn.close();
} catch (SQLException e) {
e.printStackTrace();
}
}
if(st != null){
try {
st.close();
} catch (SQLException e) {
e.printStackTrace();
}
}
}
}
package com.ljh.lesson05;
import com.ljh.lesson02.util.JdbcUtils;
import com.ljh.lesson05.utils.JdbcUtils_DBCP;
import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;
public class TestDBCP {
public static void main(String[] args) {
Connection conn = null;
PreparedStatement st = null;
ResultSet res = null;
try {
conn = JdbcUtils_DBCP.getConnection();//获取数据库连接
//select * from users where `name` = 'li' and `password` = '123456'
String sql = "select * from users where `name` = ? and `password` = ?";
st = conn.prepareStatement(sql);//预编译sql,先写sql,然后不执行
//手动给参赋值
st.setString(1,"li");
st.setString(2,"123456");
//执行cha
res = st.executeQuery();
while(res.next()){
System.out.println(res.getObject("name"));
}
} catch (SQLException e) {
e.printStackTrace();
}finally {
JdbcUtils_DBCP.release(conn,st,res);
}
}
}
C3P0
需要用到的jar包
c3p0-0.9.5.5.jar、mchange-commons-java-0.2.19.jar
<c3p0-config>
<default-config>
<property name="driverClass">com.mysql.jdbc.Driver</property>
<property name="jdbcUrl">jdbc:mysql://localhost/test</property>
<property name="user">root</property>
<property name="password">123456</property>
<property name="initialPoolSize">10</property>
<property name="maxIdleTime">30</property>
<property name="maxPoolSize">100</property>
<property name="minPoolSize">10</property>
<property name="maxStatements">200</property>
</default-config>
<!-- This app is massive! -->
<named-config name="intergalactoApp">
<property name="acquireIncrement">50</property>
<property name="initialPoolSize">100</property>
<property name="minPoolSize">50</property>
<property name="maxPoolSize">1000</property>
<!-- intergalactoApp adopts a different approach to configuring statement caching -->
<property name="maxStatements">0</property>
<property name="maxStatementsPerConnection">5</property>
<!-- he's important, but there's only one of him -->
<user-overrides user="master-of-the-universe">
<property name="acquireIncrement">1</property>
<property name="initialPoolSize">1</property>
<property name="minPoolSize">1</property>
<property name="maxPoolSize">5</property>
<property name="maxStatementsPerConnection">50</property>
</user-overrides>
</named-config>
</c3p0-config>
package com.ljh.lesson05.utils;
import com.mchange.v2.c3p0.ComboPooledDataSource;
import org.apache.commons.dbcp.BasicDataSourceFactory;
import javax.sql.DataSource;
import java.io.InputStream;
import java.sql.Connection;
import java.sql.ResultSet;
import java.sql.SQLException;
import java.sql.Statement;
import java.util.Properties;
public class JdbcUtils_C3P0 {
//代码式
private static ComboPooledDataSource dataSource= null;
static {
try{
//创建数据源 工厂模式-->创建
//这是走默认的default的数据源,
// 可以配置其他的数据源如Mysql等,在括号加字符串“mysql”
dataSource = new ComboPooledDataSource();//配置文件写法
} catch (Exception e) {
e.printStackTrace();
}
}
//获取连接
public static Connection getConnection() throws SQLException {
return dataSource.getConnection();
}
//释放连接资源
public static void release(Connection conn, Statement st, ResultSet rs){
if(rs != null){
try {
rs.close();
} catch (SQLException e) {
e.printStackTrace();
}
}
if(conn != null){
try {
conn.close();
} catch (SQLException e) {
e.printStackTrace();
}
}
if(st != null){
try {
st.close();
} catch (SQLException e) {
e.printStackTrace();
}
}
}
}
package com.ljh.lesson05;
import com.ljh.lesson05.utils.JdbcUtils_C3P0;
import com.ljh.lesson05.utils.JdbcUtils_DBCP;
import java.sql.Connection;
import java.sql.PreparedStatement;
import java.sql.ResultSet;
import java.sql.SQLException;
public class TestC3P0 {
public static void main(String[] args) {
Connection conn = null;
PreparedStatement st = null;
ResultSet res = null;
try {
conn = JdbcUtils_C3P0.getConnection();//获取数据库连接
//select * from users where `name` = 'li' and `password` = '123456'
String sql = "select * from users where `name` = ? and `password` = ?";
st = conn.prepareStatement(sql);//预编译sql,先写sql,然后不执行
//手动给参赋值
st.setString(1,"li");
st.setString(2,"123456");
//执行cha
res = st.executeQuery();
while(res.next()){
System.out.println(res.getObject("name"));
}
} catch (SQLException e) {
e.printStackTrace();
}finally {
JdbcUtils_C3P0.release(conn,st,res);
}
}
}
Apache有哪些项目
附加:
Mysql十大优化技巧
Mysql各种索引区别:
普通索引:最基本的索引,没有任何限制
唯一索引:与"普通索引"类似,不同的就是:索引列的值必须唯一,但允许有空值。
主键索引:它 是一种特殊的唯一索引,不允许有空值。
全文索引:仅可用于 MyISAM 表,针对较大的数据,生成全文索引很耗时好空间。
组合索引:为了更多的提高mysql效率可建立组合索引,遵循”最左前缀“原则。
Mysql索引会失效的几种情况分析
正确理解Mysql的列索引和多列索引
mysql通关面试宝典
问题处理方案积累
1.报错8200 - Unsupported multi schema change:更改不了表结构,比如字段说明修改都不行
处理方式: 修改ids_dev_info中字段说明:设备型号,有无ARM
ALTER TABLE ids-web-dev-info
.ids_dev_info
MODIFY COLUMN dev_model
varchar(64) CHARACTER SET utf8mb4 NULL DEFAULT ‘’ COMMENT ‘设备型号’ AFTER dev_alias
, ALGORITHM=COPY;
ALTER TABLE ids-web-dev-info
.ids_dev_info
MODIFY COLUMN pn_code
varchar(32) CHARACTER SET utf8mb4 NULL DEFAULT NULL COMMENT ‘有无ARM标识’ AFTER sn_code
, ALGORITHM=COPY;
使用ALGORITHM=COPY