zoukankan      html  css  js  c++  java
  • java实现交替打印的四种方法

    交替打印就是要实现线程间通信,有两种方式:

    1Object对象中的wait和notify(因为是交替打印,只需唤醒一个线程,所以不需要notifyAll)

     1 package com.nmcc.thread;
     2 
     3 import java.util.concurrent.ExecutorService;
     4 import java.util.concurrent.Executors;
     5 
     6 /**
     7  * TODO
     8  *
     9  * @author nmcc
    10  * @version V1.0
    11  * @date 2021-08-24 08:49
    12  *
    13  */
    14 public class SyncRunTwo {
    15 
    16     public static Object a_o = new Object();
    17     public static Object b_o = new Object();
    18     public static Object c_o = new Object();
    19 
    20     public static void main(String[] args) throws InterruptedException {
    21         ExecutorService executor = Executors.newFixedThreadPool(3);
    22         executor.execute(new BuszThread("C", c_o, b_o));
    23         executor.execute(new BuszThread("B", b_o, a_o));
    24         executor.execute(new BuszThread("A", a_o, c_o));
    25         Thread.sleep(1000);
    26 
    27         synchronized (c_o){
    28             c_o.notify();
    29         }
    30     }
    31 
    32     public static class BuszThread implements Runnable {
    33 
    34         private String name;
    35         private Object take;
    36         private Object waitFor;
    37         public BuszThread(String name, Object take, Object waitFor){
    38             this.name = name;
    39             this.take = take;
    40             this.waitFor = waitFor;
    41         }
    42         @Override
    43         public void run() {
    44             System.out.println(name + " 开始执行");
    45 
    46                 while (true) {
    47                     synchronized (waitFor) {
    48                         try {
    49                             System.out.println(name + " 开始等待它需要的条件");
    50                             waitFor.wait();
    51                             System.out.println(name + " 获得了它需要的等待条件");
    52                             Thread.sleep(1000);
    53                             System.out.println(name + " 执行完成,并释放它持有的等待条件");
    54                         } catch (InterruptedException e) {
    55                             e.printStackTrace();
    56                         }
    57                     }
    58 
    59                     synchronized (take){
    60                         take.notify();
    61                     }
    62             }
    63 
    64         }
    65     }
    66 }

    2使用lock中的Condition

     1 package com.nmcc.thread;
     2 
     3 import java.util.concurrent.ExecutorService;
     4 import java.util.concurrent.Executors;
     5 import java.util.concurrent.atomic.AtomicBoolean;
     6 import java.util.concurrent.locks.Condition;
     7 import java.util.concurrent.locks.Lock;
     8 import java.util.concurrent.locks.ReentrantLock;
     9 
    10 /**
    11  * TODO
    12  *
    13  * @author nmcc
    14  * @version V1.0
    15  * @date 2021-08-24 08:49
    16  *
    17  */
    18 public class SyncRun {
    19     private static Lock lock = new ReentrantLock(false);
    20     private static Condition a_c = lock.newCondition();
    21     private static Condition b_c = lock.newCondition();
    22     private static Condition c_c = lock.newCondition();
    23 
    24     public static void main(String[] args) throws InterruptedException {
    25         ExecutorService executor = Executors.newFixedThreadPool(3);
    26         executor.execute(new BuszThread("C", c_c, b_c, false));
    27         executor.execute(new BuszThread("B", b_c, a_c, false));
    28         executor.execute(new BuszThread("A", a_c, c_c, false));
    29         Thread.sleep(1000);
    30         lock.lock();
    31         try {
    32             c_c.signal();
    33         } finally {
    34             lock.unlock();
    35         }
    36 
    37 
    38     }
    39 
    40     public static class BuszThread implements Runnable {
    41 
    42         private String name;
    43         private Condition take;
    44         private Condition waitFor;47         public BuszThread(String name, Condition take, Condition waitFor){
    48             this.name = name;
    49             this.take = take;
    50             this.waitFor = waitFor;52         }
    53         @Override
    54         public void run() {
    55             System.out.println(name + " 开始执行");
    56             while (true){
    57                 lock.lock();
    58                 try {
    59                     System.out.println(name + " 开始等待它需要的条件");
    60                     waitFor.await();
    61                     System.out.println(name + " 获得了它需要的等待条件");
    62                     Thread.sleep(1000);
    63                     System.out.println(name + " 执行完成,并释放它持有的等待条件");
    64                     take.signal();
    65 
    66                 } catch (InterruptedException e) {
    67                     e.printStackTrace();
    68                 }finally {
    69                     lock.unlock();
    70                 }
    71             }
    72         }
    73     }
    74 }

    这两种方式,首先都需要获取到锁,然后等待他需要的前置条件,前置条件执行后,轮到他执行,然后它再去释放他持有的前置条件,

    Condition是一个lock实例出来的,他们获取的都市一个lock的锁,而如果要调用object的wait和notify方法,首先要获取对应的object的锁。

    3使用原子变量,这种方式其实不是线程间通信,他是用原子变量的比较并替换原子,让两个线程去交替的替换成功。

    package com.nmcc.thread;
    
    import java.util.concurrent.LinkedBlockingQueue;
    import java.util.concurrent.ThreadPoolExecutor;
    import java.util.concurrent.TimeUnit;
    import java.util.concurrent.atomic.AtomicInteger;
    
    /**
     * 两个线程交替打印奇偶数
     *
     * @author nmcc
     * @version V1.0
     * @date 2021-09-02 16:53
     */
    public class SyncPrint {
    
       private static AtomicInteger num = new AtomicInteger(0);
    
        public static void main(String[] args) {
            ThreadPoolExecutor executor = new ThreadPoolExecutor(2,2,60, TimeUnit.SECONDS,new LinkedBlockingQueue<>());
    
            executor.execute(new Printer(num, 0, "A"));
            executor.execute(new Printer(num, 1, "B"));
        }
    
       public static class Printer implements Runnable{
           private AtomicInteger num;
           private Integer start;
           private Integer step = 1;
           private String name;
    
           public Printer(AtomicInteger num, Integer start, String name) {
               this.num = num;
               this.start = start;
               this.name = name;
           }
    
           @Override
           public void run() {
               try {
                   while (true){
                       Integer update = start + step;
                       Thread.sleep(1000);
                       if (num.compareAndSet(start, update)){
                           System.out.println(name + " say: " + update);
                           start +=2;
                           Thread.sleep(1000);
                       }
                   }
               } catch (InterruptedException e) {
                   e.printStackTrace();
               }
           }
       }
    }

    4使用阻塞队列

     1 package com.nmcc.thread;
     2 
     3 import java.util.concurrent.ExecutorService;
     4 import java.util.concurrent.Executors;
     5 import java.util.concurrent.LinkedBlockingQueue;
     6 
     7 /**
     8  * TODO
     9  *
    10  * @author nmcc
    11  * @version V1.0
    12  * @date 2021-08-24 08:49
    13  *
    14  */
    15 public class SyncRunThree {
    16 
    17     public static LinkedBlockingQueue<Integer> queue = new LinkedBlockingQueue<Integer>(1);
    18     public static void main(String[] args) throws InterruptedException {
    19         ExecutorService executor = Executors.newFixedThreadPool(3);
    20         executor.execute(new BuszThread("C", queue));
    21         executor.execute(new BuszThread("B", queue));
    22         executor.execute(new BuszThread("A", queue));
    23         Thread.sleep(1000);
    24         queue.put(1);
    25     }
    26 
    27     public static class BuszThread implements Runnable {
    28 
    29         private String name;
    30         private LinkedBlockingQueue<Integer> queue;
    31         public BuszThread(String name, LinkedBlockingQueue<Integer> queue){
    32             this.name = name;
    33             this.queue = queue;
    34         }
    35         @Override
    36         public void run() {
    37             System.out.println(name + " 开始执行");
    38 
    39                 while (true) {
    40                     try {
    41                         System.out.println(name + " 准备获取");
    42                         Integer num = queue.take();
    43                         System.out.println(name + " 获取到:" + num);
    44                         queue.put(++num);
    45                         Thread.sleep(1000);
    46                     } catch (InterruptedException e) {
    47                         e.printStackTrace();
    48                     }
    49                 }
    50             }
    51 
    52     }
    53 }
  • 相关阅读:
    【VS开发】【智能语音处理】DTW算法(语音识别)
    【VS开发】【智能语音处理】语音信号处理之(四)梅尔频率倒谱系数(MFCC)
    【VS开发】【智能语音处理】语音信号处理之(四)梅尔频率倒谱系数(MFCC)
    【VS开发】如何移植对话框?
    【VS开发】如何移植对话框?
    【VS开发】模态对话框和非模态对话框
    【VS开发】模态对话框和非模态对话框
    【VS开发】【智能语音处理】Windows下麦克风语音采集
    【VS开发】【智能语音处理】Windows下麦克风语音采集
    【VS开发】【智能语音处理】VS中声音的采集实现
  • 原文地址:https://www.cnblogs.com/nmcc33/p/15221893.html
Copyright © 2011-2022 走看看