new Thread(()->{
phone2.sms();
},“A”).start();
new Thread(()->{
phone2.sms();
},“B”).start();
}
}
class Phone2{
Lock lock= new ReentrantLock(); //细节问题 : 两把锁 它也可以拿到call的锁
public void sms(){
//lock锁必须配对,否则就会死在里面
// lock.lock();//再锁的话 要再解锁一次!
lock.lock();
try {
System.out.println(Thread.currentThread().getName()+“—”+“sms”);
call();//这里也有锁
} catch (Exception e) {
e.printStackTrace();
} finally {
lock.unlock();
//lock.unlock();
}
}
public void call(){
lock.lock();
try {
System.out.println(Thread.currentThread().getName()+“—”+“call”);
} catch (Exception e) {
e.printStackTrace();
} finally {
lock.unlock();
}
}
}
自旋锁
- 底层使用的自旋锁CAS
package lock;
import java.util.concurrent.atomic.AtomicReference;
/**
- 自旋锁
*/
public class SpinLockDemo {
// int 0
// thread null
AtomicReference atomicReference = new AtomicReference<>();
//加锁
public void myLock(){
Thread thread = Thread.currentThread();
System.out.println(Thread.currentThread().getName()+“—>> mylock”);
//自旋锁
while(!atomicReference.compareAndSet(null,thread)){
}
}
//解锁
public void myUnLock(){
Thread thread = Thread.currentThread();
System.out.println(Thread.currentThread().getName()+“—>> myUnLock”);
atomicReference.compareAndSet(thread,null);
}
}
测试类
package lock;
import java.util.concurrent.TimeUnit;
import java.util.concurrent.locks.ReentrantLock;
public class Test {
public static void main(String[] args) throws InterruptedException {
/* ReentrantLock reentrantLock = new ReentrantLock();
reentrantLock.lock();
reentrantLock.unlock(); */
//底层使用的自旋锁CAS
SpinLockDemo lock = new SpinLockDemo();
new Thread(()->{
lock.myLock();
try {
TimeUnit.SECONDS.sleep(3);
} catch (Exception e) {
e.printStackTrace();
} finally {
lock.myUnLock();
}
},“T1”).start();
TimeUnit.SECONDS.sleep(1);
new Thread(()->{
lock.myLock();
try {
TimeUnit.SECONDS.sleep(1);
} catch (Exception e) {
e.printStackTrace();
} finally {
lock.myUnLock();
}
},“T2”).start();
}
}
死锁排查
死锁测试
package lock;
import java.rmi.server.ExportException;
import java.sql.Time;
import java.util.concurrent.TimeUnit;
public class DeadLockDemo {
public static void main(String[] args) {
String lockA=“lockA”;
String lockB=“lockB”;
new Thread(new MyThread(lockA,lockB),“A”).start();
new Thread(new MyThread(lockB,lockA),“B”).start();
}
}
class MyThread implements Runnable{
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+“尝试获得”+lockB);
try{
TimeUnit.SECONDS.sleep(2);
}catch (Exception e){
e.printStackTrace();
}
synchronized (lockB){
System.out.println(Thread.currentThread().getName()+"lock "+lockB+“尝试获得”+lockA);
}
}
}
}
怎么排除死锁
Terminal
使用jps -l
定位进程号
Java高频面试专题合集解析:
当然在这还有更多整理总结的Java进阶学习笔记和面试题未展示,其中囊括了**Dubbo、Redis、Netty、zookeeper、Spring cloud、分布式、高并发等架构资料和完整的Java架构学习进阶
必看视频!获取2024年最新Java开发全套学习资料 备注Java
导图!**
更多Java架构进阶资料展示
ayer.bilibili.com/player.html?aid=1804892953)(image-https://i-blog.csdnimg.cn/blog_migrate/38e5a57660282b55905517d7d28f61b1.png)(title-必看视频!获取2024年最新Java开发全套学习资料 备注Java)]
导图!**
[外链图片转存中…(img-rTcgf1jS-1716378819298)]
更多Java架构进阶资料展示
[外链图片转存中…(img-gvTiZ1R5-1716378819298)]
[外链图片转存中…(img-Mt3uOI7e-1716378819299)]
[外链图片转存中…(img-6hVqhEPz-1716378819299)]