Несколько UDP-пакетов в Java
Один сокет может принять серию пакетов: после каждого
receive буфер и объект
DatagramPacket используют снова. На
отправке цикл вызывает send для каждой
строки, порядок на проводе обычно совпадает с
порядком вызовов на localhost.
Приёмник в цикле читает три сообщения и печатает каждое. Отправитель шлёт их на один порт:
import java.net.DatagramPacket;
import java.net.DatagramSocket;
import java.net.InetAddress;
import java.nio.charset.StandardCharsets;
import java.util.List;
import java.util.concurrent.CountDownLatch;
public class Main {
public static void main(String[] args) throws Exception {
CountDownLatch ready = new CountDownLatch(1);
int[] port = new int[1];
Thread receiver = new Thread(() -> {
try (DatagramSocket socket = new DatagramSocket(0)) {
port[0] = socket.getLocalPort();
ready.countDown();
for (int i = 0; i < 3; i++) {
byte[] buf = new byte[256];
DatagramPacket packet = new DatagramPacket(
buf,
buf.length,
);
socket.receive(packet);
String text = new String(
packet.getData(),
0,
packet.getLength(),
StandardCharsets.UTF_8,
);
System.out.println(text);
}
} catch (Exception ex) {
throw new RuntimeException(ex);
}
});
receiver.start();
ready.await();
try (DatagramSocket socket = new DatagramSocket()) {
InetAddress host = InetAddress.getByName(
"127.0.0.1",
);
for (String word : List.of("one", "two", "three")) {
byte[] data = word.getBytes(
StandardCharsets.UTF_8,
);
DatagramPacket packet = new DatagramPacket(
data,
data.length,
host,
port[0],
);
socket.send(packet);
}
}
}
}
Ответ на каждый пакет тоже можно слать в цикле на
getAddress и getPort из соответствующего
приёма. Отправитель тогда читает несколько ответов
подряд:
import java.net.DatagramPacket;
import java.net.DatagramSocket;
import java.net.InetAddress;
import java.nio.charset.StandardCharsets;
import java.util.List;
import java.util.concurrent.CountDownLatch;
public class Main {
public static void main(String[] args) throws Exception {
CountDownLatch ready = new CountDownLatch(1);
int[] port = new int[1];
Thread receiver = new Thread(() -> {
try (DatagramSocket socket = new DatagramSocket(0)) {
port[0] = socket.getLocalPort();
ready.countDown();
for (int i = 0; i < 2; i++) {
byte[] buf = new byte[256];
DatagramPacket packet = new DatagramPacket(
buf,
buf.length,
);
socket.receive(packet);
String tag = new String(
packet.getData(),
0,
packet.getLength(),
StandardCharsets.UTF_8,
);
String echo = "echo " + tag;
byte[] reply = echo.getBytes(
StandardCharsets.UTF_8,
);
DatagramPacket out = new DatagramPacket(
reply,
reply.length,
packet.getAddress(),
packet.getPort(),
);
socket.send(out);
}
} catch (Exception ex) {
throw new RuntimeException(ex);
}
});
receiver.start();
ready.await();
try (DatagramSocket socket = new DatagramSocket()) {
InetAddress host = InetAddress.getByName(
"127.0.0.1",
);
for (String word : List.of("a", "b")) {
byte[] data = word.getBytes(
StandardCharsets.UTF_8,
);
DatagramPacket packet = new DatagramPacket(
data,
data.length,
host,
port[0],
);
socket.send(packet);
}
for (int i = 0; i < 2; i++) {
byte[] buf = new byte[256];
DatagramPacket answer = new DatagramPacket(
buf,
buf.length,
);
socket.receive(answer);
System.out.println(
new String(
answer.getData(),
0,
answer.getLength(),
StandardCharsets.UTF_8,
),
);
}
}
}
}
Отправьте пять пакетов с текстами "n1" …
"n5". Приёмник выведет пять строк по
одной на пакет.
Примите три запроса и на каждый ответьте
"ok". Отправитель выведет три строки
ответа.