iT邦幫忙

2019 iT 邦幫忙鐵人賽

DAY 27
0
Software Development

30 天介紹 Java 的 Thread系列 第 27

Day 27 介紹 Guarded Suspension 模式

  • 分享至 

  • xImage
  •  

今天來介紹 Guarded Suspension 模式,它的主要目的是當條件沒有成立時會進行一直循環的等待,等待條件成立時才會進行通知繼續來執行。主要的使用情境在 Client 和 Server 連線時,如果 Server 沒有接收到 Client 的 Request 時,Server 就會一直進行等待的動作,等到有 Client 的 Request 時 Server 才會進行執行的動作。

Guarded Suspension 模式和前幾天介紹的 Balking 模式主要的差異地方在於,如果條件不成立時 Guarded Suspension 會一直進行等待執行的動作 (wait),Baling 模式是條件不成立時不會進行等待和執行。

Guarded Suspension 模式是 Single Threaded Execution 模式的進階版本,因為 Single Threaded Execution 模式是用來保護共享變數一次只能有一個執行緒存取共享變數,而 Guarded Suspension 模式有加
上條件判斷如果條件成立時才執行,沒有成有成立時就會一直進行等待的動作。

以下寫一個有關於 Guarded Suspension 模式,簡單的 Sample Code:

import java.util.LinkedList;
import java.util.Queue;

public class GuardedObject {
  private final Queue<String> queue = new LinkedList<String>();

  public synchronized String getQueue() {
    while (queue.peek() == null) {
      try {
        wait();
      } catch(Exception e) {
        throw new RuntimeException(e);
      }
    }
    return queue.remove();
  }

  public synchronized void putQueue(String str) {
    queue.offer(str);
    notify();
  }
}

GuardedObject 是一個 Guarded 物件,在 getQueue 裡面會先去判斷 queue 裡面有沒有東西如果沒有就會進行 wait 等待的動作,如果有就會把 queue 的值取出來。putQueue 就會把字串的值放入到 queue 裡面,然後通知不要等待了。

public class ExampleThread1 implements Runnable {
  private GuardedObject guarded;

  public ExampleThread1(GuardedObject guarded) {
    this.guarded = guarded;
  }

  @Override
  public void run() {
    for (int i = 1 ; i <= 10 ; i++) {
      String str = "message" + i;
      this.guarded.putQueue(str);
      try {
        Thread.sleep(1000L);
      } catch(Exception e) {
        throw new RuntimeException(e);
      }
    }
  }
}

ExampleThread1 執行緒程式主要會將字串的值放入到 guarded 物件的 queue 裡面

public class ExampleThread2 implements Runnable {
  private GuardedObject guarded;
  public ExampleThread2(GuardedObject guarded) {
    this.guarded = guarded;
  }

  @Override
  public void run() {
    while(true) {
      String message = this.guarded.getQueue();
      System.out.println(message);
    }
  }
}

ExampleThread2 執行緒程式的目的就是會將 Queue 裡面的資料取出來然後印到 console 上,主程式的呼叫如下程式:

public class Test {
  public static void main(String args[]) {
    GuardedObject guarded = new GuardedObject();
    Thread thread1 = new Thread(new ExampleThread1(guarded));
    Thread thread2 = new Thread(new ExampleThread2(guarded));
    thread1.start();
    thread2.start();
  }
}

主程式就會開啟 ExampleThread1 和 ExampleThread2,把資料放入 Queue 裡面和從 Queue 裡面取資料的執行緒程式,執行結果如下:

message1
message2
message3
message4
message5
message6
message7
message8
message9
message10

上一篇
Day 26 介紹 Single Threaded Execution 模式
下一篇
Day 28 介紹 Producer Consumer 模式
系列文
30 天介紹 Java 的 Thread30
圖片
  直播研討會
圖片
{{ item.channelVendor }} {{ item.webinarstarted }} |
{{ formatDate(item.duration) }}
直播中

尚未有邦友留言

立即登入留言