日韩性视频-久久久蜜桃-www中文字幕-在线中文字幕av-亚洲欧美一区二区三区四区-撸久久-香蕉视频一区-久久无码精品丰满人妻-国产高潮av-激情福利社-日韩av网址大全-国产精品久久999-日本五十路在线-性欧美在线-久久99精品波多结衣一区-男女午夜免费视频-黑人极品ⅴideos精品欧美棵-人人妻人人澡人人爽精品欧美一区-日韩一区在线看-欧美a级在线免费观看

歡迎訪問 生活随笔!

生活随笔

當前位置: 首頁 > 编程资源 > 编程问答 >内容正文

编程问答

简单的线程同步问题:两个线程交替执行N次【Synchronized、Lock、ArrayBlockingQueue】...

發布時間:2025/3/17 编程问答 33 豆豆
生活随笔 收集整理的這篇文章主要介紹了 简单的线程同步问题:两个线程交替执行N次【Synchronized、Lock、ArrayBlockingQueue】... 小編覺得挺不錯的,現在分享給大家,幫大家做個參考.
方法一:傳統的線程方法
import
org.apache.log4j.Logger;/*** 兩個線程執行的代碼片段要實現同步互斥的效果,它們必須用同一個Lock對象。<br/>* 鎖是上在代表要操作的資源的類的內部方法中,而不是線程代碼中。<br/>* * 樣例:<br/>* 1)、主線程執行10次循環,接著子線程執行100此循環;<br/>* 2)、重復1)操作50次,結束。<br/>* * @author wangzhu* @date 2015-3-21下午8:00:57* */ public class ThreadCommunication {public static void main(String[] args) {final Bussiness bussiness = new Bussiness();new Thread() {@Overridepublic void run() {for (int i = 0; i < 50; i++) {bussiness.main(i);}};}.start();new Thread() {@Overridepublic void run() {for (int i = 0; i < 50; i++) {bussiness.sub(i);}};}.start();}}class Bussiness {private static final Logger logger = Logger.getLogger(Bussiness.class);/*** true:主線程<br/>* false:子線程<br/>* 默認執行主線程<br/>*/private boolean mark = false;public synchronized void main(int c) {while (mark) {// 表示當前是主線程,則進入等待狀態try {this.wait();} catch (InterruptedException e) {e.printStackTrace();}}// 當不是主線程,則開始執行for (int i = 0; i < 10; i++) {logger.info(c + "==main thread====" + i);}// 表示當前是主線程mark = true;// 喚醒所有的線程this.notifyAll();}public synchronized void sub(int c) {while (!mark) {// 表示當前是子線程,則進入等待狀態try {this.wait();} catch (InterruptedException e) {e.printStackTrace();}}// 當不是子線程,則開始執行for (int i = 0; i < 100; i++) {logger.info(c + "==sub thread====" + i);}// 表示當前是子線程mark = false;// 喚醒所有的線程this.notifyAll();}}

?

?

2、JDK1.5之后(包括1.5)加入的并發包(LockCondition
import
java.util.concurrent.locks.Condition; import java.util.concurrent.locks.Lock; import java.util.concurrent.locks.ReentrantLock;import org.apache.log4j.Logger;/*** 兩個線程執行的代碼片段要實現同步互斥的效果,它們必須用同一個Lock對象。<br/>* 鎖是上在代表要操作的資源的類的內部方法中,而不是線程代碼中。<br/>* * 樣例:<br/>* 1)、主線程執行10次循環,接著子線程執行100此循環;<br/>* 2)、重復1)操作50次,結束。<br/>* * @author wangzhu* @date 2015-3-22下午9:50:11* */ public class ConditionCommunication {private static final Logger logger = Logger.getLogger(ConditionCommunication.class);/*** @param args*/public static void main(String[] args) {final Bussiness bussiness = new Bussiness();new Thread() {@Overridepublic void run() {for (int i = 0; i < 50; i++) {bussiness.sub(i);}};}.start();new Thread() {@Overridepublic void run() {for (int i = 0; i < 50; i++) {bussiness.main(i);}};}.start();}static class Bussiness {private Lock lock = new ReentrantLock();private Condition condition = lock.newCondition();/*** true:主線程<br/>* false:子線程<br/>*/private boolean mark;public void main(int k) {// 加鎖 lock.lock();try {while (mark) {// 當前是主線程,則等待try {condition.await();} catch (InterruptedException e) {e.printStackTrace();}}for (int i = 0; i < 10; i++) {logger.info(k + "==main thread====" + i);}// 標記當前執行的是主線程mark = true;// 發出信號 condition.signal();} finally {// 釋放鎖 lock.unlock();}}public void sub(int k) {// 加鎖 lock.lock();try {while (!mark) {try {condition.await();} catch (InterruptedException e) {e.printStackTrace();}}for (int i = 0; i < 100; i++) {logger.info(k + "==sub thread====" + i);}// 標記當前執行的是子線程mark = false;// 發出信號 condition.signal();} finally {// 釋放鎖 lock.unlock();}}} }

?

?

JDK中的實例:
class
BoundedBuffer {final Lock lock = new ReentrantLock();//鎖對象final Condition notFull = lock.newCondition();//寫線程條件 final Condition notEmpty = lock.newCondition();//讀線程條件 final Object[] items = new Object[100];//緩存隊列int putptr/*寫索引*/, takeptr/*讀索引*/, count/*隊列中存在的數據個數*/;public void put(Object x) throws InterruptedException {lock.lock();try {while (count == items.length)//如果隊列滿了 notFull.await();//阻塞寫線程items[putptr] = x;//賦值 if (++putptr == items.length){putptr = 0;//如果寫索引寫到隊列的最后一個位置了,那么置為0 } ++count;//個數++notEmpty.signal();//喚醒讀線程} finally {lock.unlock();}}public Object take() throws InterruptedException {lock.lock();try {while (count == 0)//如果隊列為空notEmpty.await();//阻塞讀線程Object x = items[takeptr];//取值 if (++takeptr == items.length){takeptr = 0;//如果讀索引讀到隊列的最后一個位置了,那么置為0 }--count;//個數--notFull.signal();//喚醒寫線程return x;} finally {lock.unlock();}} }

?

參考:

http://blog.csdn.net/vking_wang/article/details/9952063

?

?

3、JDK1.5并發包中的阻塞隊列(ArrayBlockingQueue
import
java.util.concurrent.ArrayBlockingQueue;import org.apache.log4j.Logger;/*** ArrayBlockingQueue(阻塞隊列)<br/>*    put(anObject):<br/>* 把anObject加到BlockingQueue里,如果BlockQueue沒有空間,<br/>* 則調用此方法的線程被阻斷,直到BlockingQueue里面有空間再繼續.<br/>* *   take():<br/>* 取走BlockingQueue里排在首位的對象,若BlockingQueue為空,<br/>* 阻斷進入等待狀態直到,BlockingQueue有新的數據被加入;<br/>* * @author wangzhu* @date 2015-3-23上午9:31:22* */ public class ArrayBlockingQueueCommunication {private static final Logger logger = Logger.getLogger(ArrayBlockingQueueCommunication.class);/*** @param args*/public static void main(String[] args) {final Bussiness bussiness = new Bussiness();new Thread() {@Overridepublic void run() {for (int i = 0; i < 50; i++) {bussiness.sub(i);}};}.start();new Thread() {@Overridepublic void run() {for (int i = 0; i < 50; i++) {bussiness.main(i);}};}.start();}static class Bussiness {// 阻塞隊列ArrayBlockingQueue<Integer> mainQuery = new ArrayBlockingQueue<Integer>(1);ArrayBlockingQueue<Integer> subQuery = new ArrayBlockingQueue<Integer>(1);{try {subQuery.put(1);} catch (InterruptedException e) {e.printStackTrace();}}public void main(int k) {try {mainQuery.put(1);} catch (InterruptedException e) {e.printStackTrace();}for (int i = 0; i < 10; i++) {logger.info(k + "==main thread====" + i);}try {subQuery.take();} catch (InterruptedException e) {e.printStackTrace();}}public void sub(int k) {try {subQuery.put(1);} catch (InterruptedException e) {e.printStackTrace();}for (int i = 0; i < 100; i++) {logger.info(k + "==sub thread====" + i);}try {mainQuery.take();} catch (InterruptedException e) {e.printStackTrace();}}} }

參考:

http://www.cnblogs.com/jackyuj/archive/2010/11/24/1886553.html

?

轉載于:https://www.cnblogs.com/xiaoxian1369/p/4356103.html

總結

以上是生活随笔為你收集整理的简单的线程同步问题:两个线程交替执行N次【Synchronized、Lock、ArrayBlockingQueue】...的全部內容,希望文章能夠幫你解決所遇到的問題。

如果覺得生活随笔網站內容還不錯,歡迎將生活随笔推薦給好友。