1. 简介
在Java中的消息传递,是指在多线程环境下,通过在不同的线程之间传递消息来进行通信的一种方式。这种方式相对于共享内存的方式来说更加安全,因为不同的线程之间不能直接修改彼此的内存状态,只能通过传递消息来进行通信。
2. 消息传递模型
Java中的消息传递模型主要有两种,分别是基于队列和基于管道。
2.1 基于队列的消息传递模型
在基于队列的消息传递模型中,每个线程都有自己的队列,通过在队列之间传递消息来进行通信。通常情况下,每个队列都是一个阻塞队列,即当队列为空时,从其中取出消息的操作会被阻塞,直到队列中有新的消息为止。
下面是一个基于队列的消息传递模型的简单示例:
import java.util.concurrent.BlockingQueue;
import java.util.concurrent.LinkedBlockingQueue;
public class MessagePassingQueueExample {
public static void main(String[] args) {
BlockingQueue<String> queue1 = new LinkedBlockingQueue<>();
BlockingQueue<String> queue2 = new LinkedBlockingQueue<>();
Thread senderThread = new Thread(() -> {
try {
queue1.put("Hello World!");
String message = queue2.take();
System.out.println(message);
} catch (InterruptedException e) {
e.printStackTrace();
}
});
Thread receiverThread = new Thread(() -> {
try {
String message = queue1.take();
queue2.put(message.toUpperCase());
} catch (InterruptedException e) {
e.printStackTrace();
}
});
senderThread.start();
receiverThread.start();
}
}
在这个示例程序中,有两个队列分别为queue1
和queue2
,并且有两个线程分别为senderThread
和receiverThread
。在senderThread
中,首先向queue1
中放入一条消息"Hello World!"
,然后从queue2
中取出一条消息,并将其打印出来。在receiverThread
中,首先从queue1
中取出一条消息,将其转换成大写之后再放回到queue2
中。
2.2 基于管道的消息传递模型
在基于管道的消息传递模型中,不同的线程之间通过管道来传递消息。通常情况下,每个线程都会有一个输入管道和一个输出管道。当一个线程向其输出管道中写入消息时,另一个线程就可以从其输入管道中读取到对应的消息。
下面是一个基于管道的消息传递模型的简单示例:
import java.io.IOException;
import java.io.PipedInputStream;
import java.io.PipedOutputStream;
public class MessagePassingPipeExample {
public static void main(String[] args) throws IOException {
PipedOutputStream output1 = new PipedOutputStream();
PipedInputStream input1 = new PipedInputStream(output1);
PipedOutputStream output2 = new PipedOutputStream();
PipedInputStream input2 = new PipedInputStream(output2);
Thread senderThread = new Thread(() -> {
try {
output1.write("Hello World!".getBytes());
output1.flush();
byte[] buffer = new byte[1024];
int length = input2.read(buffer);
String message = new String(buffer, 0, length);
System.out.println(message);
} catch (IOException e) {
e.printStackTrace();
}
});
Thread receiverThread = new Thread(() -> {
try {
byte[] buffer = new byte[1024];
int length = input1.read(buffer);
String message = new String(buffer, 0, length);
output2.write(message.toUpperCase().getBytes());
output2.flush();
} catch (IOException e) {
e.printStackTrace();
}
});
senderThread.start();
receiverThread.start();
}
}
在这个示例程序中,有两个输入和输出管道分别为input1
/output1
和input2
/output2
,并且有两个线程分别为senderThread
和receiverThread
。在senderThread
中,首先向output1
中写入一条消息"Hello World!"
,然后从input2
中读取一条消息,并将其打印出来。在receiverThread
中,首先从input1
中读取一条消息,将其转换成大写之后再写入到output2
中。