• MySql中的有条件插入 insert where


    假设现在我们有这样的需求:当数据库中不存在满足条件的记录时,可以插入一条记录,否则程序退出。该怎么实现?

    1年以上工作经验的人应该都能立即想到:去检查一下库里有没有记录,没有就插入,有就结束。

    int count = selectFromDb(); // ①
    if count > 0 {
          return;
    } else {
          insertIntoDb(); // ②
    }
    

    2年以上工作经验的在写完上面的逻辑后会立即发现:在并发场景下这样并不安全。如果两个线程同时执行到①这里,都会发现数据库没有记录,于是分别执行了②。所以在并发场景下,这里需要使用分布式锁。

    int count = selectFromDb(); // ①
    if count > 0 {
          return;
    } else {
          try (getLock()) {// ③
                count = selectFromDb(); // ④
                if (count == 0) {
                    insertIntoDb(); // ②
                }
          }
    }
    

    这里在③处加了分布式锁,然后看一下的确没有数据再插入。

    这篇文章要说的是使用数据库的sql执行机制来保证并发锁的实现。当然了,如果条件允许,使用唯一键冲突也是可以的。

    在我们日常处理数据的时候,都是可以使用条件的,比如最简单的select where,最普通的update where等等。如果我们在插入的时候也可以使用where这个问题不就解决了吗。

    当然了,正因为mysql没有提供这种语法,所以我们才在这里讨论这个问题。

    mysql提供了根据已有数据来插入表的机制,就是非著名的insert select。所以我们的突破口就在这里,既然这里有select我们就在这里的select加where,因为insert select的实现是select不出东西的时候是不会插入的。
    所以这里我们这样写

    insert into t(id, c1, c2) select 1, "","" from dual where not exists (select * from t where c1="")
    

    这里的where c1=""假设就是我们的条件①。

  • 相关阅读:
    cookie和session的区别?
    请画出Servlet 2.2以上Web Application的基本目录结构
    简述HttpSession的作用、使用方法,可用代码说明
    Request对象的主要方法
    什么情况下调用doGet()和doPost()?
    SERVLET API中forward()与redirect()的区别?
    Servlet的基本架构
    说一说Servlet的生命周期
    解释一下什么是servlet?
    基数排序
  • 原文地址:https://www.cnblogs.com/somefuture/p/14105436.html
Copyright © 2020-2023  润新知