码迷,mamicode.com
首页 > 数据库 > 详细

mysql 不存在则插入

时间:2018-03-11 19:14:12      阅读:176      评论:0      收藏:0      [点我收藏+]

标签:extra   not   直接   unsigned   des   into   warning   存在   insert   

主要看在事务中不存在则插入的阻塞情况。

表定义:

mysql> desc user;
+-------------+------------------+------+-----+-------------------+----------------+
| Field       | Type             | Null | Key | Default           | Extra          |
+-------------+------------------+------+-----+-------------------+----------------+
| id          | int(10) unsigned | NO   | PRI | NULL              | auto_increment |
| name        | varchar(50)      | NO   | MUL | NULL              |                |
| password    | char(20)         | NO   |     | NULL              |                |
| regist_time | timestamp        | NO   |     | CURRENT_TIMESTAMP |                |
+-------------+------------------+------+-----+-------------------+----------------+
4 rows in set (0.00 sec)

client1:

mysql> begin;
Query OK, 0 rows affected (0.00 sec)

mysql> select * from user;
+----+------+----------+---------------------+
| id | name | password | regist_time         |
+----+------+----------+---------------------+
|  1 | a    | a        | 2018-03-11 16:32:43 |
|  2 | b    | b        | 2018-03-11 16:33:09 |
|  3 | c    | c        | 2018-03-11 16:33:39 |
+----+------+----------+---------------------+
3 rows in set (0.00 sec)

mysql> insert into user(name,password) select ‘d‘,‘d‘ from dual where not exist (select name from user where name=‘d‘);
Query OK, 1 row affected (0.00 sec)
Records: 1  Duplicates: 0  Warnings: 0 mysql
> select * from user; +----+------+----------+---------------------+ | id | name | password | regist_time | +----+------+----------+---------------------+ | 1 | a | a | 2018-03-11 16:32:43 | | 2 | b | b | 2018-03-11 16:33:09 | | 3 | c | c | 2018-03-11 16:33:39 | | 4 | d | d | 2018-03-11 17:03:35 | +----+------+----------+---------------------+ 4 rows in set (0.00 sec)

然后启动client2:

mysql> begin;
Query OK, 0 rows affected (0.00 sec)

mysql> select * from user;
+----+------+----------+---------------------+
| id | name | password | regist_time         |
+----+------+----------+---------------------+
|  1 | a    | a        | 2018-03-11 16:32:43 |
|  2 | b    | b        | 2018-03-11 16:33:09 |
|  3 | c    | c        | 2018-03-11 16:33:39 |
+----+------+----------+---------------------+
3 rows in set (0.00 sec)

mysql> select * from user where name=d;
Empty set (0.02 sec)

mysql> insert into user (name,password) select d,d from dual where not exists (select name from user where name=d);

client2 执行“ insert into user (name,password) select ‘d‘,‘d‘ from dual where not exists (select name from user where name=‘d‘); ”出现阻塞,直到超时或client1 commit。

client2 直接执行插入操作则不会阻塞:

mysql> insert into user(name, password) values (d,d);
Query OK, 1 row affected (0.00 sec)

client2 执行:

mysql> insert into user (name,password) select e,e from dual where not exists (select name from user where name=e);

也会出现阻塞,可见,这种情况使用的是表锁。另:如果已经存在name=‘d‘的数据,client1执行"insert not exists"后并不会使用表锁,client2执行时不会阻塞。

client1 查询后commit:

mysql> select * from user;
+----+------+----------+---------------------+
| id | name | password | regist_time         |
+----+------+----------+---------------------+
|  1 | a    | a        | 2018-03-11 16:32:43 |
|  2 | b    | b        | 2018-03-11 16:33:09 |
|  3 | c    | c        | 2018-03-11 16:33:39 |
|  4 | d    | d        | 2018-03-11 17:03:35 |
+----+------+----------+---------------------+
4 rows in set (0.00 sec)

mysql> commit;
Query OK, 0 rows affected (0.04 sec)

client2 查询后commit:

mysql> select * from user;
+----+------+----------+---------------------+
| id | name | password | regist_time         |
+----+------+----------+---------------------+
|  1 | a    | a        | 2018-03-11 16:32:43 |
|  2 | b    | b        | 2018-03-11 16:33:09 |
|  3 | c    | c        | 2018-03-11 16:33:39 |
|  5 | d    | d        | 2018-03-11 17:36:16 |
+----+------+----------+---------------------+
4 rows in set (0.00 sec)

mysql> commit;
Query OK, 0 rows affected (0.04 sec)

注意client1 和 client2 name=‘d‘的id。

 

另:on duplicate key只适用于unique key,如果不是unique,总是会插入

mysql> insert into user(name,password) values(d,d) on duplicate key update password=e;

这时会插入一条name=‘d‘,password=‘d‘的记录。

mysql 不存在则插入

标签:extra   not   直接   unsigned   des   into   warning   存在   insert   

原文地址:https://www.cnblogs.com/drizzlewithwind/p/8545138.html

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!