Java UDP套接字 - 数据留在服务器端

标签 java sockets udp

我正在通过使用 UDP 套接字在 Java 中实现一个非常基本的服务器-客户端模型,我遇到了一个非常奇怪的问题。

我想做的就是让用户(客户端)向服务器发送消息,然后服务器打印它。

我有一个示例,但由于存在以下问题,我遗漏了一些内容:

如果客户端向服务器发送消息“a”,它会被正确接收。 如果客户端向服务器发送消息“bbb”,它会被正确接收。 如果客户端向服务器发送消息“c”,则服务器将打印“cbb”作为接收到的消息。

似乎服务器在收到新消息时确实清理了某种缓冲区。

这是我使用的代码:

服务器

import java.net.DatagramPacket;
import java.net.DatagramSocket;
import java.net.InetAddress;



public class UDPServer {
public static void main(String args[]) throws Exception {
    byte[] receive_data = new byte[256];
    int recv_port;

    DatagramSocket server_socket = new DatagramSocket(5000);

    System.out.println("Server - Initialized server. Waiting for client on port 5000");

    while (true) {
        // System.out.println("Server - Listening for connections...");
        DatagramPacket receive_packet = new DatagramPacket(receive_data, receive_data.length);
        
        server_socket.receive(receive_packet);
        
        String data = new String(receive_packet.getData());

        InetAddress IPAddress = receive_packet.getAddress();

        recv_port = receive_packet.getPort();

        if (data.equals("q") || data.equals("Q")) {
            System.out.println("Server - Exiting !");
            break;
        } else {
            System.out.println("Server - Client from IP " + IPAddress + " @ port " + recv_port + " said : " + data + " (length: " + receive_packet.getLength() + ")");
        }
    }
}
}

客户端

public class UDPClient {
public static void main(String args[]) throws Exception {
    byte[] send_data = new byte[256];

    BufferedReader infromuser = new BufferedReader(new InputStreamReader(System.in));

    DatagramSocket client_socket = new DatagramSocket();

    InetAddress IPAddress = InetAddress.getByName("localhost");

    System.out.println("Client - Initialized the client...");

    while (true) {
        System.out.print("Client - Type Something (q or Q to quit): ");

        String data = infromuser.readLine();

        if (data.equals("q") || data.equals("Q")) {
            System.out.println("Client - Exited !");
            DatagramPacket send_packet = new DatagramPacket(send_data, send_data.length, IPAddress, 5000);
            System.out.println("Client - Sending data : <" + data + ">");
            client_socket.send(send_packet);
            break;
        } else {
            send_data = data.getBytes();
            DatagramPacket send_packet = new DatagramPacket(send_data, send_data.length, IPAddress, 5000);
            System.out.println("Client - Sending data : <" + data + ">");
            client_socket.send(send_packet);
        }
    }

    client_socket.close();
}
}

我想这个错误是微不足道的,但我的网络编程能力有限,所以我不知 Prop 体是什么。

为了清楚起见,我在同一台机器 (mac) 的不同终端上同时运行服务器和客户端,以防万一它影响了情况。

如有任何帮助,我们将不胜感激。

编辑

...然后我回来回答我自己的问题。 问题是我没有定义服务器套接字应该读取的数据量。 因此当我改变

String data = new String(receive_packet.getData());

String data = new String(receive_packet.getData(), 0, receive_packet.getLength());

一切顺利。

仅供将来引用和可能遇到相同问题的人:)

最佳答案

当您根据结果构造 String 时,您目前忽略了接收到的数据包的长度。

使用后DataSocket.receive(DatagramPacket)DatagramPacket的长度应设置为实际接收到的长度:

The length field of the datagram packet object contains the length of the received message. If the message is longer than the packet's length, the message is truncated.

这应该可以解决接收方的问题:

String data = new String(receive_packet.getData(), 0, receive_packet.getLength());

为此,您还需要确保发送的数据大小合适。特别是,不要使用 send_data.length 来构造传出的 DatagramPacket。这将始终使用缓冲区的全长)。长度参数并不意味着总是 send_data.length(否则构造函数会从数组中获取它本身),它意味着该数组中消息的实际有用长度。

关于Java UDP套接字 - 数据留在服务器端,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/8973427/

相关文章:

sockets - 关于 Java EE 的问题?

c# - UDPClient 流略有延迟。我可以加快速度吗?

java - 发送 GET 请求后,HttpURLConnection 返回响应代码 500,即使它在本地工作

java - 将字符串中的各种字母大写

java - 步骤内的 Spring 批处理

c - HTTP 代理服务器保持事件连接支持

actionscript-3 - 在 AS3 中通过套接字发送语音的更好方法

c++ - 通过 UDP 发送时的不同结果

C#套接字数据报溢出

java - 在 Scala 中使用从 Java 导入的不可变 "val"