死锁和排查

1.什么是死锁?如何产生

通俗的来说死锁就是两个或两个以上的进程由于竞争资源而导致阻塞,在没有外力的作用下,这种阻塞会一直持续下去。产生死锁有以下四大原因:

   ①互斥:一个资源同时只能被一个线程占用。②请求和保持:因为请求资源而阻塞的线程不会放弃自己已经拥有的资源。 ③不剥夺:阻塞的线程所拥有的资源不能被其他的线程强行剥夺。④循环等待:多个资源形成头尾相连,循环等待的关系。

2.具体的代码实现

下面程序是非常标准的写法,给一个线程方法传入两个不同的参数,再开启两个线程就会导致死锁。

public class DeadLock {
    public static void main(String[] args) {

        String lockA = "lockA";
        String lockB = "lockB";

        new Thread(new MyThread(lockA,lockB),"T1").start();
        new Thread(new MyThread(lockB,lockA),"T2").start();
    }
}

class MyThread extends Thread{

    private String lockA;
    private String lockB;

    public MyThread(String lockA, String lockB) {
        this.lockA = lockA;
        this.lockB = lockB;
    }

    @Override
    public void run() {
          synchronized(lockA){
              System.out.println(Thread.currentThread().getName() + "lock:" + lockA + "=>get"+lockB);
              try {
                  TimeUnit.SECONDS.sleep(2);
              } catch (InterruptedException e) {
                  e.printStackTrace();
              }
              synchronized (lockB){
                  System.out.println(Thread.currentThread().getName() + "lock:" + lockB + "=>get"+lockA);
              }
          }
    }
}

3.如何排查死锁?

 ①使用gps -l查看全部的进程,可以看到deadlock的进程号

  ②使用jstack可以查看此进程的堆栈信息

 通过堆栈信息我们看出线程1拥有资源94530同时等待944f8,线程二拥有944f8等待94530,造成死锁。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
MySQL死锁是数据库并发操作中常见的问题,当两个或更多的事务在执行过程中相互等待对方释放资源时,就会形成死锁。这通常发生在两个事务分别持有对方需要的锁时,导致彼此都无法继续执行。要排查MySQL死锁,可以按照以下步骤进行: 1. **查看死锁信息**: - 使用`SHOW ENGINE INNODB STATUS`命令,它会显示当前InnoDB引擎中的锁定情况,包括可能的死锁信息。 2. **确定死锁事务ID**: - 在死锁日志(通常是`ib_logfile0`或`ib_logfile1`)中查找死锁消息,会有一个事务ID列表,这些事务正在等待锁定。 3. **分析事务日志**: - 使用`mysqladmin`的`force-recovery`选项读取事务日志,尝试回滚事务,看看是否能解除死锁。但是要小心,这可能会导致数据丢失。 4. **使用`SHOW PROCESSLIST`**: - 查看所有活动的连接(进程),检查哪些事务处于活跃状态,以及它们的锁模式和锁定的行。 5. **手动解锁**: - 对于已经识别出的死锁事务,可以通过`KILL`命令强制结束,但需要谨慎,因为这可能破坏数据一致性。 6. **锁定策略调整**: - 检查应用程序的锁定策略,确保不会无意识地创建死锁条件,比如避免循环依赖锁。 7. **定期检查锁定表**: - 查看`INFORMATION_SCHEMA`.`LOCKS`表,了解哪些资源被锁定,以及锁定的时间长度,以便判断是否存在长时间的死锁。 8. **设置死锁检测参数**: - MySQL有`innodb_lock_wait_timeout`参数,可以设置超时限制以避免长时间的等待,但如果频繁触发,可能需要优化锁的获取顺序或程序逻辑。 相关问题-- 1. 如何在MySQL中查看死锁日志? 2. 死锁发生时,如何在不破坏数据的情况下结束事务? 3. 如何防止应用程序产生过多的死锁
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值