两个线程交替打印1-100,列举以下几种方法:
- synchronized+object:
wait()等待,notify() 唤醒
- Lock-condition(条件变量):
c1.signalAll() 唤醒,c2.await() 等待
- volatile 修饰的变量,通过值控制(可以是boolean,或者是数字类型)
- Semaphore(信号量),
acquire()获取许可,release()释放许可;
- CyclicBarrier(循环栅栏),
await() 使等待
- AtomicBoolean,基于cas机制实现线程交替打印
- LockSupport:
park()阻塞当前线程、unpark(Thread t) 释放t线程,设置锁标志位
Object(等待+唤醒)
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34
|
public class WaitNotifyStagger { private static final Object o1 = new Object(); private volatile int num = 0;
private void printf() { do { synchronized (o1) { o1.notify();
System.out.println(Thread.currentThread().getName() + "-" + (++num)); try { o1.wait(2000); } catch (InterruptedException e) { e.printStackTrace(); } } }while (num < 100); }
public static void main(String[] args) { WaitNotifyStagger threadPrint = new WaitNotifyStagger();
new Thread(threadPrint::printf, "A").start(); new Thread(threadPrint::printf, "B").start(); } }
|
Condition(条件变量)
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35
| public class ThreadStaggerByCondition { private static final Lock lock = new ReentrantLock(); private static final ExecutorService threadPool = Executors.newFixedThreadPool(3); private static int num = 0;
public void print(Condition curr, Condition next) { do { try { lock.lockInterruptibly(); next.signal();
System.out.println(Thread.currentThread().getName() + "-" + (++num));
curr.await(2, TimeUnit.SECONDS); } catch (InterruptedException e) { e.printStackTrace(); } finally { lock.unlock(); } } while (num < 90); }
public static void main(String[] args) { ThreadStaggerByCondition threadPrint2 = new ThreadStaggerByCondition(); Condition condition1 = lock.newCondition(); Condition condition2 = lock.newCondition(); Condition condition3 = lock.newCondition();
threadPool.submit(() -> threadPrint2.print(condition1, condition2)); threadPool.submit(() -> threadPrint2.print(condition2, condition3)); threadPool.submit(() -> threadPrint2.print(condition3, condition1));
threadPool.shutdown(); } }
|
Semaphore(信号量)
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30
| public class ThreadStaggerBySemaphore { private int num = 1; private int maxNum = 40;
private void print(Semaphore curr, Semaphore next) { while (num < maxNum) { try { curr.acquire();
System.out.println(Thread.currentThread().getName() + "-" + (num++));
next.release(); } catch (InterruptedException e) { e.printStackTrace(); } } }
public static void main(String[] args) { final ExecutorService threadPool = Executors.newFixedThreadPool(2); final Semaphore semaphore1 = new Semaphore(1); final Semaphore semaphore2 = new Semaphore(0);
ThreadStaggerBySemaphore stagger = new ThreadStaggerBySemaphore(); threadPool.submit(() -> stagger.print(semaphore1, semaphore2)); threadPool.submit(() -> stagger.print(semaphore2, semaphore1));
threadPool.shutdown(); } }
|
CyclicBarrier(循环栅栏)
主要用于让一组线程互相等待,直到所有线程都达到了一个公共屏障点(Barrier Point),然后这些线程才继续执行。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38
| public class ThreadStaggerByCyclicBarrier { private static volatile int num = 0; private static int maxNum = 40; private static final CyclicBarrier cyclicBarrier = new CyclicBarrier(2); static volatile boolean flag = true;
public static void main(String[] args) { new Thread(() -> { do { if (flag) { System.out.println(Thread.currentThread().getName() + "-" + (++num)); } flag = false; try { cyclicBarrier.await(); } catch (Exception e) { e.printStackTrace(); } } while (num < maxNum); }).start();
new Thread(() -> { do { if (!flag) { System.out.println(Thread.currentThread().getName() + "-" + (++num)); } flag = true; try { cyclicBarrier.await(); } catch (Exception e) { e.printStackTrace(); } } while (num < maxNum); }).start(); } }
|
Queue(阻塞队列)
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32
| public class ThreadStaggerByQueue { private static volatile int num = 0; private static final int maxNum = 40;
public void print(BlockingQueue<Integer> curr, BlockingQueue<Integer> next) { do { try { curr.take();
System.out.println(Thread.currentThread().getName() + "-" + (++num));
next.add(0); } catch (InterruptedException e) { e.printStackTrace(); } } while (num < maxNum); }
public static void main(String[] args) { final ExecutorService threadPool = Executors.newFixedThreadPool(3); final BlockingQueue<Integer> q1 = new LinkedBlockingQueue<Integer>() {{ add(0); }}; final BlockingQueue<Integer> q2 = new LinkedBlockingQueue<>();
ThreadStaggerByQueue threadPrint2 = new ThreadStaggerByQueue(); threadPool.submit(() -> threadPrint2.print(q1, q2)); threadPool.submit(() -> threadPrint2.print(q2, q1));
threadPool.shutdown(); } }
|
volatile 变量
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35
|
public class VolatileStagger { static volatile boolean flag = true; private static int num = 0;
public static void main(String[] args) { new Thread(() -> { do { if (flag) { System.out.println(Thread.currentThread().getName() + "-" + (++num)); flag = false; } } while (num < 100);
}, "A").start();
new Thread(() -> {
for (; num < 100; ) { if (!flag) { System.out.println(Thread.currentThread().getName() + "-" + (++num)); flag = true; } }
}, "B").start(); } }
|
AtomicBoolean(CAS)
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35
|
public class AtomicStagger { static volatile AtomicBoolean flag = new AtomicBoolean(true); private static int num = 0;
public static void main(String[] args) { new Thread(() -> { do { if (flag.get()) { System.out.println(Thread.currentThread().getName() + "-" + (++num)); flag.set(false); } } while (num < 100);
}, "A").start();
new Thread(() -> {
for (; num < 100; ) { if (!flag.get()) { System.out.println(Thread.currentThread().getName() + "-" + (++num)); flag.set(true); } }
}, "B").start(); } }
|
LockSupport(阻塞/释放)
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36
|
public class LockSupportStagger { private static int num = 0; static Thread t1 = null; static Thread t2 = null;
public static void main(String[] args) { t1 = new Thread(() -> { do { LockSupport.park(); System.out.println(Thread.currentThread().getName() + "-" + (++num)); LockSupport.unpark(t2); } while (num < 100); }, "A"); t2 = new Thread(() -> { do { LockSupport.park(); System.out.println(Thread.currentThread().getName() + "-" + (++num)); LockSupport.unpark(t1); } while (num < 100); }, "B");
t1.start(); t2.start(); LockSupport.unpark(t1); } }
|