当我从套接字接收到一些数据时,为啥会附加很多空格?

Posted

技术标签:

【中文标题】当我从套接字接收到一些数据时,为啥会附加很多空格?【英文标题】:Why lots of spaces append when I received some data from sockets?当我从套接字接收到一些数据时,为什么会附加很多空格? 【发布时间】:2013-03-14 11:50:13 【问题描述】:

您好,我正在编写一个简单的 java 程序来从套接字读取数据,但遇到了一个问题,每次输入后都会出现很多空格。

目标:编写一个简单的服务器套接字,它可以从客户端套接字读取正确的数据。

到目前为止:我已经能够编写从套接字读取的代码,甚至能够读取数据,但问题是我最后得到了很多空格。

所以只好用了trim(),最后来管理空间,但还是不知道是对是错。

不胜感激。

注意:我正在使用 windows7 telnet 服务连接到套接字。

readSocket() 
    System.out.println(client_socket);
    try 
        System.out.println("reading socket");
        /*BufferedReader brIn = new BufferedReader(new InputStreamReader(client_socket.getInputStream()));
        String inputLine = null;
        while ((inputLine = brIn.readLine()) != null) 
            System.out.println(inputLine);
        */
        InputStream is = client_socket.getInputStream();
        byte[] byteArr = new byte[1024];
        int inputsize = -1;
        int currentPos = 0;
        StringBuffer sb = new StringBuffer(11111);
        /*while((inputsize = is.read(byteArr)) != -1) 
            String processed = new String(byteArr);
            sb.append(processed);
        */
        int BUFFER_SIZE = 1024;
        int read;
        byte[] buffer = new byte[BUFFER_SIZE];
        String processed = "";
        while ((read = is.read(byteArr, 0, BUFFER_SIZE)) != -1) 
            String current = new String(byteArr);
            //os.write(buffer, 0, read);
            System.out.println("current Process   "+current);

            //processed +=current;
            sb.append(current.toString().trim());
        
        System.out.println("Socket input is : "+sb.toString());
        System.out.println("Sending response to client  "+processed.toString());
        //client_socket.getOutputStream().write(sb.toString().getBytes());
        //client_socket.getOutputStream().close();

        FileOutputStream fos = new FileOutputStream(new File("C:\\Users\\himanshu2100\\eee.txt"));
        fos.write(processed.getBytes());
        fos.close();
        is.close();
        client_socket.close();
     catch (IOException e) 
        // TODO Auto-generated catch block
        e.printStackTrace();
    

根据 Roger Lindsjö 和 mprivat 的建议,我重新设计了从流中读取的部分。

readSocket() 
    System.out.println(client_socket);
    try 
        System.out.println("reading socket");
        InputStream is = client_socket.getInputStream();
        byte[] byteArr = new byte[1024];

        int read;
        int BUFFER_SIZE = 1024;

        ByteArrayOutputStream baos = new ByteArrayOutputStream();

        while ((read = is.read(byteArr, 0, BUFFER_SIZE)) != -1) 
            baos.write(byteArr, 0, read);   //This is an optimized design, instead of having so many strings
        
        System.out.println("Output is :"+new String(baos.toByteArray()));
        baos.close();
        is.close();
        client_socket.close();
     catch (IOException e) 
        // TODO Auto-generated catch block
        e.printStackTrace();
    

我希望这是一个更好的解决方案,所以发布它。欢迎提出建议。

【问题讨论】:

【参考方案1】:

在这条线上:while ((read = is.read(byteArr, 0, BUFFER_SIZE)) != -1)

read 将包含实际读取的字节数,因此如果您的服务器发送字符串“CORRECT”但您的BUFFER_SIZE 是 1024,您将有很多额外空间,因此您不能这样做:@987654324 @。相反,您必须只使用从流中读取的字节:

String current = new String(byteArr, 0, read);

【讨论】:

【参考方案2】:

当您读入一个数组时,整个数组可能不会被填充。 read 变量将包含实际读取的字节数。

    while ((read = is.read(byteArr, 0, BUFFER_SIZE)) != -1) 
        String current = new String(byteArr, 0, read);
        System.out.println("current Process   "+current);
        sb.append(current);
    

如果您使用多字节编码,上述可能无法正常工作,因为字符的每个部分都可能在单独的读取中,这会创建无效序列。

【讨论】:

这意味着我应该首先将所有数据移动到字节数组中,然后当从套接字读取完成时,然后传输到字符串或任何其他介质。

以上是关于当我从套接字接收到一些数据时,为啥会附加很多空格?的主要内容,如果未能解决你的问题,请参考以下文章

jQuery mobile:当我将选择菜单附加到不同页面上的另一个 DOM 节点时,为啥会中断?

在UDP Socket java android上发送和接收数据

当我从单独的视图控制器中删除核心数据实体时,为啥会调用 UITableView 方法?

为啥你认为当我从我的 CF 卡上传图像到我的电脑时,有些图像会随机损坏?

为啥对 recv 的重叠调用会返回 ERROR_NO_MORE_ITEMS(259)?

XDP 套接字附加到的事件是啥?