• JDK5.0 特性-线程同步装置之Semaphore


    来自:http://www.cnblogs.com/taven/archive/2011/12/17/2291474.html

      1 import java.util.ArrayList;
      2 
      3 import java.util.concurrent.ExecutorService;
      4 
      5 import java.util.concurrent.Executors;
      6 
      7 import java.util.concurrent.Semaphore;
      8 
      9 import java.util.concurrent.locks.Lock;
     10 
     11 import java.util.concurrent.locks.ReentrantLock;
     12 
     13  
     14 
     15 /**
     16 
     17  *Java 5.0里新增加了4个协调线程间进程的同步装置,它们分别是:Semaphore,CountDownLatch,CyclicBarrier和Exchanger
     18 
     19  *Semaphore可以控制运行线程的个数
     20 
     21  *Semaphore是一个用来管理资源池的工具,可以看成是个通行证,线程要想从资源池拿到资源必须先拿到通行证,如果线程暂时拿不到通告证,线程就会被阻断,进入等待状态.
     22 
     23  */
     24 
     25 /**
     26 
     27  *使用Semaphore的关键技术点如下:
     28 
     29  *1.在构造Semaphore对象时,必须提供通行证的数目,如"newSemaphore(3)"将创建一个具有3个通行证的Semaphore对象,一旦该对象被创建,其通行证数量是不能改变的.
     30 
     31  *2.Semaphore的acquire方法取得一个通行证,如果通行证已经发完了,当前线程将进入等待状态,直到有其他线程释放了通行证.
     32 
     33  *3.Semaphore的release方法释放了资源池.
     34 
     35  */
     36 
     37 public class SemaphoreTest {
     38 
     39        /**
     40 
     41         * 模拟资源池的类
     42 
     43         * 只为池发放2个通行证,即同时只允许2个线程获得池中的资源
     44 
     45         */
     46 
     47        public static class Pool{
     48 
     49               ArrayList<String> pool = null;  //保存资源池中的资源
     50 
     51               Semaphore pass = null; //通行证
     52 
     53               Lock lock = new ReentrantLock();
     54 
     55               public Pool(int size){
     56 
     57                      //初始化资源池
     58 
     59                      pool = new ArrayList<String>();
     60 
     61                      for(int i = 0; i < size; i++){
     62 
     63                             pool.add("Resource " + i);
     64 
     65                      }
     66 
     67                      //发送2个通行证
     68 
     69                      pass = new Semaphore(2);
     70 
     71               }
     72 
     73               public String get()throws InterruptedException{
     74 
     75                      //获取通行证,只有得到通行证后才能得到资源
     76 
     77                      System.out.println("Try to get a pass...");
     78 
     79                      pass.acquire();
     80 
     81                      System.out.println("Got a pass");
     82 
     83                      return getResource();
     84 
     85               }
     86 
     87               private String getResource(){
     88 
     89                      lock.lock();
     90 
     91                      String result = pool.remove(0);
     92 
     93                      System.out.println("资源 " + result + "被取走");
     94 
     95                      lock.unlock();
     96 
     97                      return result;
     98 
     99               }
    100 
    101               public void put(String resource){
    102 
    103                      //归还通行证,并那还资源
    104 
    105                      System.out.println("Released a pass");
    106 
    107                      pass.release();
    108 
    109                      releaseResource(resource);
    110 
    111               }
    112 
    113               private void releaseResource(String resource){
    114 
    115                      lock.lock();
    116 
    117                      System.out.println("资源 " + resource + " 被归还");
    118 
    119                      pool.add(resource);
    120 
    121                      lock.unlock();
    122 
    123               }
    124 
    125        }
    126 
    127        public static void testPool(){
    128 
    129               //准备10个资源的资源池
    130 
    131               final Pool aPool = new Pool(10);
    132 
    133               Runnable worker = new Runnable(){
    134 
    135                      @Override
    136 
    137                      public void run() {
    138 
    139                             String resource = null;
    140 
    141                             try{
    142 
    143                                    resource = aPool.get();//取得resource
    144 
    145                                    //用resource做工作
    146 
    147                                    System.out.println("I finished on " + resource);
    148 
    149                                    Thread.sleep(500);
    150 
    151                                    System.out.println("I finished on " + resource);
    152 
    153                             }catch(InterruptedException ex){
    154 
    155                             }
    156 
    157                             aPool.put(resource);
    158 
    159                      }                          
    160 
    161               };
    162 
    163               //启动5个任务
    164 
    165               ExecutorService service = Executors.newCachedThreadPool();
    166 
    167               for(int i = 0; i<5; i++){
    168 
    169                      service.submit(worker);
    170 
    171               }
    172 
    173               service.shutdown();
    174 
    175        }
    176 
    177        public static void main(String... args){
    178 
    179               SemaphoreTest.testPool();
    180 
    181        }
    182 
    183 }
  • 相关阅读:
    Linux查看进程运行的完整路径方法
    http chunked编码格式
    剑指offer 26. 树的子结构
    101. 对称二叉树
    http长链接处理不当引发的问题
    linux gstack pstack 进程运行堆栈查看工具 strip
    96. 不同的二叉搜索树
    LeetCode350. 两个数组的交集 II
    C++ Vector转Set与Set转Vector
    Go语言学习笔记十五--Go语言map的基本操作
  • 原文地址:https://www.cnblogs.com/sunxucool/p/3842620.html
Copyright © 2020-2023  润新知