Java:使用Java.util.concurrent线程访问读取线程串行端口

时间:2010-07-31 21:08:58

标签: java multithreading concurrency serial-port

我正在尝试编写Java串行设备驱动程序,并希望使用(new to me)java.util.concurrent包。我有一种方法发送数据包然后等待ACK。我打算有炭。接待运行在一个不同的线程。如果接收线程获得ACK,它应该通过发送数据包功能通知线程。接收线程实现状态机,并应通知任何侦听器已解码的数据包。

我想我知道如何使用直接线程,waitnotify等来做到这一点,但我不知道如何使用新的并发包执行此操作。非常感谢任何指针。

1 个答案:

答案 0 :(得分:4)

使用CyclicBarrier。以下是Javadoc的相关内容:

  

一种同步辅助工具,允许一组线程全部等待彼此到达公共障碍点。 CyclicBarriers在涉及固定大小的线程方的程序中很有用,这些线程必须偶尔等待彼此。屏障称为循环,因为它可以在等待线程释放后重新使用。

因此,您需要为多个CyclicBarrier方创建2并让接收方线程在ACK之后调用await()并让发送方线程在之前调用await()做SEND。

这是一个SSCCE,可以帮助您入门。

package com.stackoverflow.q3379797;

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

public class Test {

    public static void main(String[] args) {
        CyclicBarrier barrier = new CyclicBarrier(2);
        Receiver receiver = new Receiver(barrier);
        Sender sender = new Sender(barrier);

        ExecutorService executor = Executors.newFixedThreadPool(2);
        executor.submit(receiver);
        executor.submit(sender);
    }

}

class Receiver implements Runnable {

    private CyclicBarrier barrier;

    public Receiver(CyclicBarrier barrier) {
        this.barrier = barrier;
    }

    @Override
    public void run() {
        while (true) {
            try {
                // Wait for ACK (the sleep just simulates that).
                Thread.sleep(2000);
                System.out.println("ACK");

                // Then notify.
                barrier.await();
            } catch (Exception e) {
                e.printStackTrace();
            }
        }
    }
}

class Sender implements Runnable {

    private CyclicBarrier barrier;

    public Sender(CyclicBarrier barrier) {
        this.barrier = barrier;
    }

    @Override
    public void run() {
        while (true) {
            try {
                // Wait for notify.
                barrier.await();

                // Now do SEND.
                System.out.println("SEND");
            } catch (Exception e) {
                e.printStackTrace();
            }
        }
    }
}

您将在标准输出中看到以下内容:

(2 seconds)
ACK
SEND
(2 seconds)
ACK
SEND
(2 seconds)
ACK
SEND