java实现自定义同步组件的过程

Posted 努力追上曾经的自己

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了java实现自定义同步组件的过程相关的知识,希望对你有一定的参考价值。

实现同步组件twinsLock:可以允许两个线程同时获取到锁,多出的其它线程将被阻塞。

 

以下是自定义的同步组件类,一般我们将自定义同步器Sync定义为同步组件TwinsLock的静态内部类。

实现同步器需要继承AbstractQueuedSynchronizer并覆盖相应的方法。

package com.lock;

import java.util.concurrent.TimeUnit;
import java.util.concurrent.locks.AbstractQueuedSynchronizer;
import java.util.concurrent.locks.Condition;
import java.util.concurrent.locks.Lock;

public class TwinsLock implements Lock {
private final Sync sync=new Sync(2);
//自定义一个同步器,作为自定义同步组件的静态内部类
private static final class Sync extends AbstractQueuedSynchronizer{
Sync(int count){
if(count<=0){
throw new IllegalArgumentException("count must large than zero");
}
setState(count);//设置同步状态

}
/**
* 尝试以共享方式获取同步状态
* return 大于0时表示获取成功
*/
@Override
public int tryAcquireShared(int reduceCount){
for(;;){
int current=getState();
int newCount=current-reduceCount;
if(newCount<0||compareAndSetState(current, newCount)){
return newCount;
}
}
}
/**
* 同步器中的释放同步状态的方法
*/
@Override
public boolean tryReleaseShared(int returnCount){
for(;;){
int current=getState();
int newCount=current+returnCount;
if(compareAndSetState(current, newCount)){
return true;
}
}
}
}

@Override
public void lock() {
sync.acquireShared(1);
}

@Override
public void unlock() {
sync.releaseShared(1);
}


@Override
public void lockInterruptibly() throws InterruptedException {
// TODO Auto-generated method stub

}

@Override
public Condition newCondition() {
// TODO Auto-generated method stub
return null;
}

@Override
public boolean tryLock() {
// TODO Auto-generated method stub
return false;
}

@Override
public boolean tryLock(long arg0, TimeUnit arg1)
throws InterruptedException {
// TODO Auto-generated method stub
return false;
}

}

 

下面是测试类,注意将线程实现类放在方法内和放在方法外时,对线程共享变量的区别

1,

package com.lock;

import java.util.concurrent.locks.Lock;

public class TwinsLockTest {

public static void main(String[] str) throws InterruptedException {
//将内部类放在方法内部,共享变量必须定义为final
final Lock twinsLock=new TwinsLock();
class Worker extends Thread{
public void run(){
while(true){
twinsLock.lock();

try{
Thread.sleep(10000);
System.out.println(Thread.currentThread().getName());
Thread.sleep(10000);
}catch(Exception e){
e.printStackTrace();
}finally{
twinsLock.unlock();
}
}
}

}
for(int i=0;i<10;i++){
Worker worker=new Worker();
worker.setDaemon(true);
worker.start();
}
for(int i=0;i<10;i++){
Thread.sleep(500000);
System.out.println("....................");
}

}

}

 

 

2,

package com.lock;

import java.util.concurrent.locks.Lock;

public class TwinsLockTest2 {
//将外部类放在方法外面,共享变量必须定义为static才能保证同步。不然的话每个线程对象都拥有一个共享变量的拷贝
static Lock twinsLock=new TwinsLock();
public static void main(String[] str) throws InterruptedException {


for(int i=0;i<10;i++){
Worker worker=new TwinsLockTest2().new Worker();
worker.setDaemon(true);
worker.start();
}
for(int i=0;i<10;i++){
Thread.sleep(500000);
System.out.println("....................");
}

}

class Worker extends Thread{
public void run(){
while(true){
twinsLock.lock();

try{
Thread.sleep(2000);
System.out.println(Thread.currentThread().getName());
Thread.sleep(2000);
}catch(Exception e){
e.printStackTrace();
}finally{
twinsLock.unlock();
}
}
}

}

}

 








































































































































以上是关于java实现自定义同步组件的过程的主要内容,如果未能解决你的问题,请参考以下文章

《Java并发编程的艺术》--Java中的锁

如何实现自定义同步组件

Java并发编程 AbstractQueuedSynchronizer的设计与实现

java中的锁

深入浅出Java并发编程指南「实战篇」教你如何使用AbstractQueuedSynchronizer实现自己的同步器组件

手把手教你构建源码级组件——Java互斥不可重入锁