1.概述
用DatagramSocket与DatagramPacket实现UDP通信.
UDP比TCP相对来说简单一点,不需要等待连接,且处理数据不需要用输出输出流,只需要DatagramPacket.严格来说,UDP没有服务端和客户端之分,只有发送端与接收端之分.
2.发送端
发送端首先建立DatagramSocket与DatagramPacket,设置好DatagramPacket的端口与ip,再通过DatagramSocket发送.
(1)创建DatagramSocket与DatagramPacket
DatagramSocket socket = new DatagramSocket(55555);
这里的55555端口是指数据通过这个端口发送.
(2)创建DatagramPacket
1InetAddress ip = InetAddress.getByName("127.0.0.1"); 2int port = 12345; 3String message = "message"; 4DatagramPacket packet = new DatagramPacket(message.getBytes(),message.getBytes().length,ip,port);
构造方法DatagramPacket()的四个参数分别为
- 发送的字节数组
- 字节数组长度
- ip
- 端口
这里端口不能与上面的一致,不然的话会提示端口被占用.
(3)发送
socket.send(packet);
3.接收端
接收端只需指定端口进行接收,这里的端口在DatagramSocket中的构造方法中指定,与发送端的发送的packet中设置的端口一致.
(1)创建DatagramSocket
DatagramSocket socket = new DatagramSocket(12345);
(2)创建DatagramPacket
这里创建的DatagramPacket只需要指定存储数据的字节数组与该字节数组的长度.
1byte [] message = new byte[2048]; 2DatagramPacket packet = new DatagramPacket(message, message.length);
(3)接收
socket.receive(packet);
这个方法会阻塞,直到接收到packet.
(4)获取数据
接收到packet后可以使用getData()获取数据,返回字节数组,可以传递给String的构造方法创建String.
String str = new String(packet.getData());
4.完整代码
这里人为地设定了客户端与服务端,可以互相发送数据,服务端输入后发送到服务端,服务端返回固定数据, "客户端"与"服务端"轮流扮演了发送端与接收端的角色.配合了swing使用.
(1)Server.java
1import java.io.DataInputStream; 2import java.io.DataOutputStream; 3import java.io.IOException; 4import java.net.DatagramPacket; 5import java.net.DatagramSocket; 6import java.net.InetAddress; 7import java.net.ServerSocket; 8import java.net.Socket; 9import javax.swing.*; 10 11public class Server 12{ 13 public static void main(String[] args) 14 { 15 JFrame frame = new JFrame("Server"); 16 JTextArea text = new JTextArea(); 17 18 frame.add(text); 19 frame.setSize(600, 300); 20 frame.setLocationRelativeTo(null); 21 frame.setVisible(true); 22 frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE); 23 24 try 25 { 26 byte [] message = new byte[2048]; 27 DatagramSocket socket = new DatagramSocket(12345); 28 DatagramPacket packet = new DatagramPacket(message, message.length); 29 socket.receive(packet); 30 31 InetAddress ip = packet.getAddress(); 32 int port = packet.getPort(); 33 text.setText("ip : "+ip.toString()+"\n"); 34 text.append("port : "+port+"\n"); 35 text.append("message : "+new String(packet.getData())); 36 37 String messageFromServer = "Message from server"; 38 packet = new DatagramPacket(messageFromServer.getBytes(),messageFromServer.getBytes().length,ip,port); 39 socket.send(packet); 40 socket.close(); 41 } 42 catch (IOException e) 43 { 44 e.printStackTrace(); 45 } 46 } 47}
(2)Client.java
1import java.io.DataInputStream; 2import java.io.DataOutputStream; 3import java.io.IOException; 4import java.net.DatagramPacket; 5import java.net.DatagramSocket; 6import java.net.InetAddress; 7import java.net.Socket; 8 9import javax.swing.*; 10import java.awt.GridLayout; 11public class Client 12{ 13 public static void main(String[] args) { 14 JFrame frame = new JFrame(); 15 JTextArea text = new JTextArea(); 16 JButton send = new JButton("send"); 17 GridLayout layout = new GridLayout(2,1,1,1); 18 19 frame.setLayout(layout); 20 frame.setTitle("Client"); 21 frame.setVisible(true); 22 frame.setLocationRelativeTo(null); 23 frame.setSize(600, 300); 24 frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE); 25 26 frame.add(text); 27 frame.add(send); 28 send.addActionListener( v-> 29 { 30 try 31 { 32 InetAddress ip = InetAddress.getByName("127.0.0.1"); 33 int port = 12345; 34 DatagramSocket socket = new DatagramSocket(55555); 35 String message = text.getText(); 36 DatagramPacket packet = new DatagramPacket(message.getBytes(),message.getBytes().length,ip,port); 37 socket.send(packet); 38 39 byte [] messageFromServer = new byte[2048]; 40 packet = new DatagramPacket(messageFromServer, messageFromServer.length); 41 socket.receive(packet); 42 text.setText(new String(packet.getData())); 43 socket.close(); 44 } 45 catch (IOException e) 46 { 47 e.printStackTrace(); 48 } 49 }); 50 } 51}
5.测试
