您的位置:首页 > 其它

从头认识多线程-2.4 锁的可重入性

2016-04-27 22:38 387 查看
这一章节我们来讨论一下锁的可重入性。
1.什么是可重入锁?
一个线程在执行一个带锁的方法,该方法中又调用了另一个需要相同锁的方法,则该线程可以直接执行调用的方法,而无需重新获得锁。

2.特性:
(1)同一对象,不同方法,可以获取同样的锁,然后重入

package com.ray.deepintothread.ch02.topic_5;

public class ReGetInTheLock {
public static void main(String[] args) throws InterruptedException {
MyTestObjectOne myTestObjectOne = new MyTestObjectOne();
ThreadOne threadOne = new ThreadOne(myTestObjectOne);
Thread thread = new Thread(threadOne);
thread.start();
}
}

class ThreadOne implements Runnable {

private MyTestObjectOne myTestObjectOne;

public ThreadOne(MyTestObjectOne myTestObjectOne) {
this.myTestObjectOne = myTestObjectOne;
}

@Override
public void run() {
myTestObjectOne.service_1();
}
}

class MyTestObjectOne {
public synchronized void service_1() {
System.out.println("service_1 begin");
service_2();
System.out.println("service_1 end");
}

public synchronized void service_2() {
System.out.println("service_2 begin");
service_3();
System.out.println("service_2 end");
}

public synchronized void service_3() {
System.out.println("service_3 begin");
System.out.println("service_3 end");
}
}

输出:
service_1 begin
service_2 begin
service_3 begin
service_3 end
service_2 end
service_1 end

(2)继承关系,父子获取同样的锁

package com.ray.deepintothread.ch02.topic_5;

public class ReGetInTheLock2 {
public static void main(String[] args) throws InterruptedException {
Sub sub = new Sub();
ThreadTwo threadTwo = new ThreadTwo(sub);
Thread thread = new Thread(threadTwo);
thread.start();
}
}

class ThreadTwo implements Runnable {

private Sub sub;

public ThreadTwo(Sub sub) {
this.sub = sub;
}

@Override
public void run() {
sub.show();
}
}

class Father {
public void show() {
System.out.println("father show");
}
}

class Sub extends Father {
@Override
public void show() {
System.out.println("sub show");
super.show();
}
}

输出:
sub show
father show

3.使用场景
解决自旋锁的死锁问题
自旋锁实例:

public class SpinLock {

private AtomicReference<Thread> sign =new AtomicReference<>();

public void lock(){
Thread current = Thread.currentThread();
while(!sign .compareAndSet(null, current)){
}
}

public void unlock (){
Thread current = Thread.currentThread();
sign .compareAndSet(current, null);
}
}

关于Atomic的几个方法
getAndSet() : 设置新值,返回旧值.
compareAndSet(expectedValue, newValue) : 如果当前值(current value)等于期待的值(expectedValue), 则原子地更新指定值为新值(newValue), 如果更新成功,返回true, 否则返回false, 换句话可以这样说: 将原子变量设置为新的值, 但是如果从我上次看到的这个变量之后到现在被其他线程修改了(和我期望看到的值不符), 那么更新失败

(其实笔者还没有使用过原子类的操作,所以解释的不清不楚)
都是引用自:http://blog.csdn.net/jationxiaozi/article/details/6322151

总结:这一章节展现了可重入锁以及它的特性。

这一章节就到这里,谢谢
------------------------------------------------------------------------------------
我的github:https://github.com/raylee2015/DeepIntoThread

目录:/article/7548544.html
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: