Android setContentView源碼與原理分析

一、概念

Semaphore也是一個線程同步的輔助類,可以維護當(dāng)前訪問自身的線程個數(shù),并提供了同步機制。使用Semaphore可以控制同時訪問資源的線程個數(shù),例如,實現(xiàn)一個文件允許的并發(fā)訪問數(shù)。

二、Semaphore的主要方法:

void acquire():從此信號量獲取一個許可,在提供一個許可前一直將線程阻塞,否則線程被中斷。
  void release():釋放一個許可,將其返回給信號量。
  int availablePermits():返回此信號量中當(dāng)前可用的許可數(shù)。
  boolean hasQueuedThreads():查詢是否有線程正在等待獲取。
三、為什么要用Semaphore
Semaphore有兩個目的,第一個是多個共享資源互斥使用,第二個是并發(fā)線程數(shù)的控制,具體例子如下:

WX20201116-162836.png

6個線程同時執(zhí)行一個工作,只允許最多3個同時執(zhí)行,由上圖可以看出,release() 釋放資源的順序不一定遵循進入的順序。

import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
import java.util.concurrent.Semaphore;

public class SemaphoreTest {


    public static void main(String[] args) {
        testSemaphore();
    }

    public static void testSemaphore() {
        ExecutorService executorService = Executors.newCachedThreadPool();
        final Semaphore semaphore = new Semaphore(3);
        for (int i = 0; i < 10; i++) {
            try {
                Thread.sleep(200);

                Runnable runnable = new Runnable() {
                    @Override
                    public void run() {
                        try {
                            //請求獲得許可,如果有可獲得的許可則繼續(xù)往下執(zhí)行,許可數(shù)減1。否則進入阻塞狀態(tài)
                            semaphore.acquire();
                        } catch (InterruptedException e) {
                            e.printStackTrace();
                        }
                        System.out.println("線程" + Thread.currentThread().getName() +
                                "進入,當(dāng)前已有" + (3 - semaphore.availablePermits()) + "個并發(fā)");
                        try {
                            Thread.sleep((long) (Math.random() * 10000));
                        } catch (InterruptedException e) {
                            e.printStackTrace();
                        }
                        System.out.println("線程" + Thread.currentThread().getName() +
                                "即將離開");
                        semaphore.release();//釋放許可,許可數(shù)加1
                        //下面代碼有時候執(zhí)行不準確,因為其沒有和上面的代碼合成原子單元
                        System.out.println("線程" + Thread.currentThread().getName() +
                                "已離開,當(dāng)前已有" + (3 - semaphore.availablePermits()) + "個并發(fā)");

                    }
                };
                executorService.execute(runnable);
            } catch (InterruptedException e) {
                e.printStackTrace();
            }
        }
    }


}

三、 同ReentrantLock比較,Semaphore內(nèi)部也是依靠一個繼承自AbstractQueuedSynchronizer的Sync抽象類型的類成員變量sync來實現(xiàn)主要功能的, 單個信號量的Semaphore對象可以實現(xiàn)互斥鎖的功能,并且可以是由一個線程獲得了“鎖”,再由另一個線程釋放“鎖”,這可應(yīng)用于死鎖恢復(fù)的一些場合。

import java.sql.BatchUpdateException;
import java.util.concurrent.ExecutorService;
import java.util.concurrent.Executors;
import java.util.concurrent.Semaphore;
import java.util.concurrent.locks.Lock;
import java.util.concurrent.locks.ReentrantLock;

public class LockTest {

    public static void main(String[] args) {
        final Business business = new Business();
        ExecutorService executorService = Executors.newCachedThreadPool();
        executorService.execute(new Runnable() {
            @Override
            public void run() {
                business.service();
            }
        });
    }

    private static class Business {
        private int count;
        Lock lock = new ReentrantLock();
        Semaphore sp = new Semaphore(1);

        public void service() {
            //lock.lock();
            try {
                sp.acquire(); //當(dāng)前線程使用count變量的時候?qū)⑵滏i住,不允許其他線程訪問
            } catch (InterruptedException e1) {
                e1.printStackTrace();
            }
            try {
                count++;
                try {
                    Thread.sleep(1000);
                } catch (InterruptedException e) {
                    e.printStackTrace();
                }
                System.out.println(count);
            } catch (RuntimeException e) {
                e.printStackTrace();
            } finally {
                //lock.unlock();
                sp.release();  //釋放鎖
            }
        }
    }
}

最后編輯于
?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
【社區(qū)內(nèi)容提示】社區(qū)部分內(nèi)容疑似由AI輔助生成,瀏覽時請結(jié)合常識與多方信息審慎甄別。
平臺聲明:文章內(nèi)容(如有圖片或視頻亦包括在內(nèi))由作者上傳并發(fā)布,文章內(nèi)容僅代表作者本人觀點,簡書系信息發(fā)布平臺,僅提供信息存儲服務(wù)。

相關(guān)閱讀更多精彩內(nèi)容

  • Semaphore (信號量)是由計算機科學(xué)家Dijkstra在1965年提出的,廣泛應(yīng)用不同的操作系統(tǒng),在管程提...
    yes的練級攻略閱讀 500評論 0 0
  • 一個計數(shù)信號量。從概念上來說,一個Semaphore維護了一組permits【許可證】。每次調(diào)用acquire()...
    編碼之路從零開始閱讀 432評論 0 0
  • Semaphore是一種基于計數(shù)的信號量。它可以設(shè)定一個閾值,基于此,多個線程競爭獲取許可信號,做完自己的申請后歸...
    在遠方的你等我閱讀 479評論 0 1
  • Semaphore的工作原理以及實例Semphore 是一種在多線程環(huán)境下使用的設(shè)施,該設(shè)施負責(zé)協(xié)調(diào)各個線程,以保...
    滔滔逐浪閱讀 332評論 0 0
  • 一、概述 Semaphore(信號量) 是一個線程同步結(jié)構(gòu),用于在線程間傳遞信號,以避免出現(xiàn)信號丟失,或者像鎖一樣...
    阮小貳閱讀 2,034評論 0 3

友情鏈接更多精彩內(nèi)容