我们在开发数据库相关的逻辑过程中, 经常检查表中是否已经存在这样的一条记录, 如果存在则更新或者不做操作, 如果没有存在记录,则需要插入一条新的记录。

这样的逻辑固然可以通过两条sql语句完成。

SELECT COUNT(*) FROM xxx WHERE ID=xxx;
if (x == 0)
INSERT INTO xxx VALUES;
else
UPDATE xxx SET ;

 

但是这样操作在性能上有所损失, 代码结构感觉有点丑陋。其实Mysql提供了可以在一个SQL语句中完成上述逻辑的支持。

方案一:REPLACE语法

replace的语法格式为:

1. replace into table_name(col_name, …) values(…)

2. replace into table_name(col_name, …) select …

3. replace into table_name set col_name=value, …

算法说明:

REPLACE的运行与INSERT很相像,但是如果旧记录与新记录有相同的值,则在新记录被插入之前,旧记录被删除,即:

1. 尝试把新行插入到表中

2. 当因为对于主键或唯一关键字出现重复关键字错误而造成插入失败时:

从表中删除含有重复关键字值的冲突行

再次尝试把新行插入到表中

旧记录与新记录有相同的值的判断标准就是:表有一个PRIMARY KEY或UNIQUE索引,否则,使用一个REPLACE语句没有意义。

该语句会与INSERT相同,因为没有索引被用于确定是否新行复制了其它的行。

返回值:

REPLACE语句会返回一个数,来指示受影响的行的数目。该数是被删除和被插入的行数的和。

受影响的行数可以容易地确定是否REPLACE只添加了一行,或者是否REPLACE也替换了其它行:检查该数是否为1(添加)或更大(替换)。

示例:

eg:(phone字段为唯一索引)

replace into table_name(email,phone,user_id) values(‘test569′,’99999′,’123′)

另外:在 SQL Server 中可以这样处理:

if not exists (select phone from t where phone= ‘1’)

insert into t(phone, update_time) values(‘1′, getdate())

else

update t set update_time = getdate() where phone= ‘1’

更多信息请看:http://dev.mysql.com/doc/refman/5.1/zh/sql-syntax.html#replace

方案二:ON DUPLICATE KEY UPDATE

如上所写,你也可以在INSERT INTO…..后面加上 ON DUPLICATE KEY UPDATE方法来实现。

如果您指定了ON DUPLICATE KEY UPDATE,并且插入行后会导致在一个UNIQUE索引或PRIMARY KEY中出现重复值,

则执行旧行UPDATE。例如,如果列a被定义为UNIQUE,并且包含值1,则以下两个语句具有相同的效果:
mysql>INSERT INTO table (a,b,c) VALUES (1,2,3)

->ON DUPLICATE KEY UPDATE c=c+1;

mysql>UPDATE table SET c=c+1 WHERE a=1;

如果行作为新记录被插入,则受影响行的值为1;如果原有的记录被更新,则受影响行的值为2。

注释:如果列b也是唯一列,则INSERT与此UPDATE语句相当:

mysql> UPDATE table SET c=c+1 WHERE a=1 OR b=2 LIMIT 1;

如果a=1 OR b=2与多个行向匹配,则只有一个行被更新。通常,您应该尽量避免对带有多个唯一关键字的表使用ON DUPLICATE KEY子句。

您可以在UPDATE子句中使用VALUES(col_name)函数从INSERT…UPDATE语句的INSERT部分引用列值。

换句话说,如果没有发生重复关键字冲突,则UPDATE子句中的VALUES(col_name)可以引用被插入的col_name的值。本函数特别适用于多行插入。VALUES()函数只在INSERT…UPDATE语句中有意义,其它时候会返回NULL。

mysql> INSERT INTO table (a,b,c) VALUES (1,2,3),(4,5,6)

-> ON DUPLICATE KEY UPDATE c=VALUES(a)+VALUES(b);

本语句与以下两个语句作用相同:

mysql> INSERT INTO table (a,b,c) VALUES (1,2,3)

-> ON DUPLICATE KEY UPDATE c=3;

mysql> INSERT INTO table (a,b,c) VALUES (4,5,6)

-> ON DUPLICATE KEY UPDATE c=9;

当您使用ON DUPLICATE KEY UPDATE时,DELAYED选项被忽略。

示例:

例子1:向一个表里写入数据时,如果没有相关数据就插入,如果有了就更新相关值。

(displayid为主键)

INSERT INTO
cdqsscms_house_hot_top (displayid,x1,x2,x3,x4,x5,last_updated)
VALUES(2820,1,63,79,54,45,1311053750)
ON DUPLICATE KEY UPDATE
x1=x1+ 1,
x2=x2+ 63,
x3=x3+ 79,
x4=x4+ 54,
x5=x5+ 45,
last_updated= 1311053750

例子2(结合 select ..from…):将一个表的数据导入到另外一个表中,数据的重复性就得考虑(如下)。

唯一索引为:email

INSERT INTO table_name1(title,first_name,last_name,email,phone,user_id,role_id,status,campaign_id)

SELECT ”,”,”,table_name2.email,table_name2.phone,NULL,NULL,’pending’,29

FROM table_name2

WHERE table_name2.status = 1

ON DUPLICATE KEY UPDATE table_name1.status = ‘pending’

语句的关键地方,都已高亮出来~

其它关键:DELAYED 做为快速插入,并不是很关心失效性,提高插入性能。

IGNORE 只关注主键对应记录是不存在,无则添加,有则忽略。

特别说明:在MYSQL中UNIQUE 索引将会对null字段失效,也就是说(a字段上建立唯一索引):

insert into test(a) values(null)

insert into test(a) values(null)

比如想往表中插入一条数据,如果表中没有该条数据才插入,如果已经存在该条数据就不插入。

首先,在创建表时,将不需要重复的字段设置为unique,然后在插入时,使用insert ignore语句。

例如:(数据库用的是mysql5)
创建一张表用来存储用户:
create table user_info
(
   uid mediumint(10) unsigned NOT NULL auto_increment primary key,
   last_name char(20) not null,
   first_name char(20) not null,
   unique ( last_name, first_name)
);
alter table anser add UNIQUE (last_name,first_name)
插入数据:
insert ignore into user_info (last_name,first_name) values ('x','y');
这样一来,如果表中已经存在last_name='x'且first_name='y'的数据,就不会插入,如果没有就会插入一条新数据。

MySql插入记录时判断的更多相关文章

  1. Mysql 插入记录时检查记录是否已经存在,存在则更新,不存在则插入记录SQL

    我们在开发数据库相关的逻辑过程中, 经常检查表中是否已经存在这样的一条记录, 如果存在则更新或者不做操作, 如果没有存在记录,则需要插入一条新的记录. 这样的逻辑固然可以通过两条sql语句完成. SE ...

  2. SqlServer和Mysql插入记录前判断是否存在,存在则插入,不存在则修改。

    SqlServer中是这样: ) ,@title,@searchKeys,@serviceIntervalSecond,@sleepMillisecondPerSearch) ELSE UPDATE ...

  3. MySQL 插入记录时自动更新时间戳

    将字段设置成timestamp类型,同时默认值设置成 CURRENT_TIMESTAMP.

  4. mysql插入数据时,中文乱码

    MySQL 插入数据时,中文乱码问题的解决(转) 当向 MySQL 数据库插入一条带有中文的数据形如 insert into employee values(null,'张三','female','1 ...

  5. (转)MySQL 插入数据时,中文乱码问题的解决

    MySQL 插入数据时,中文乱码问题的解决  原文:http://www.cnblogs.com/sunzn/archive/2013/03/14/2960248.html 当向 MySQL 数据库插 ...

  6. Mysql插入中文时提示:ERROR 1366 (HY000): Incorrect string value: '\xE5\x8F\xB0\xE5\xBC\x8F...' fo

    Mysql插入数据时提示:ERROR 1366 (HY000): Incorrect string value: ‘\xE5\x8F\xB0\xE5\xBC\x8F…’ fo 分析如下: 首先通过语句 ...

  7. MyBatis插入记录时返回主键id的方法

    有时候插入记录之后需要使用到插入记录的主键,通常是再查询一次来获取主键,但是MyBatis插入记录时可以设置成返回主键id,简化操作,方法大致有两种. 对应实体类: public class User ...

  8. mysql插入数据时 insert IGNORE、ON DUPLICATE KEY UPDATE、replace into

    转: mysql insert时几个操作DELAYED .IGNORE.ON DUPLICATE KEY UPDATE的区别 博客分类: mysql基础应用   mysql insert时几个操作DE ...

  9. Mybatis + Mysql 插入数据时中文乱码问题

    近日跟朋友一起建立一个项目,用的是spring+mybatis+mysql. 今天碰到一个mybatis向mysql中插入数据时,中文显示为'???'的问题,拿出来说下. 对于数据库操作中出现的中文乱 ...

随机推荐

  1. JAVA学习提高之----安装多个JDK版本的问题

    我的机器上最开始安装的是jdk1.6,后来因为工作需要又安装了jdk1.4.但是,环境变量我并未更改,还是指向jdk1.6的路径的.可是,在cmd窗口输入 Java -version 却得到是1.4. ...

  2. 转:如何学习SQL(第四部分:DBMS扩展功能与SQL高级话题)

    转自:http://blog.163.com/mig3719@126/blog/static/285720652010950102575/ 9. DBMS提供的扩展功能 掌握了基本的关系模型原理和DB ...

  3. iphone SE 自带视频播放器要求的视频格式转换参数

  4. python unicode字符串

    程序开发中,不同语言文字的显示,不同字符集之间的转换非常麻烦,在python的unicode的使用中,对这点感触颇深.所以,以下总结了python中对unicode字符处理的一些理解. 程序存储.传输 ...

  5. 最大似然估计(Maximum Likelihood,ML)

    先不要想其他的,首先要在大脑里形成概念! 最大似然估计是什么意思?呵呵,完全不懂字面意思,似然是个啥啊?其实似然是likelihood的文言翻译,就是可能性的意思,所以Maximum Likeliho ...

  6. android 属性

    RelativeLayout 第一类:属性值为true可false android:layout_centerHrizontal        水平居中 android:layout_centerVe ...

  7. Linq分页查询

    //Linq分页查询 int pageIndex = Convert.ToInt32(HttpContext.Current.Request["PageIndex"]); int ...

  8. robotframework笔记4

    机器人框架概述   机器人框架是一个通用的开源的自动化测试框架 验收测试和验收测试驱动开发(ATDD).它具有易于使用的表格的测试数据 语法采用关键字驱动 测试方法.其检测能力可以通过测试库 用Pyt ...

  9. HDUOJ--------A simple stone game(尼姆博弈扩展)(2008北京现场赛A题)

    A simple stone game                                                                                  ...

  10. iOS开发 iOS10推送必看

    iOS10更新之后,推送也是做了一些小小的修改,下面我就给大家仔细说说.希望看完我的这篇文章,对大家有所帮助. 一.简单入门篇---看完就可以简单适配完了 相对简单的推送证书以及环境的问题,我就不在这 ...