【问题标题】:how to write bytes to server socket如何将字节写入服务器套接字
【发布时间】:2016-03-12 00:22:07
【问题描述】:

我正在编写一个java socket程序来从服务器读取数据,我无法控制服务器,下面是协议,

  • 2字节:幻数
  • 2字节:数据长度
  • N 字节:ASCII 字符串数据负载
  • 幻数和数据长度的大端序

例如:如果我的请求是“command/1/getuserlist”,如何构造上述协议的请求匹配并将响应读回列表

我是套接字编程的新手,不知道如何构建我的请求并读回响应。

有人可以指导我如何构建请求并阅读来自

的响应

【问题讨论】:

    标签: java sockets serversocket


    【解决方案1】:

    根据规范,您必须按照以下方式构建一个数据包

    | 2 | 2 | N ........ |
    

    现在这可能很容易,有多种方法可以做到,我建议你一种:

    import java.nio.ByteBuffer;
    import java.nio.ByteOrder;
    
    static byte[] buildPacket(int magicNumber, String payload) throws UnsupportedEncodingException
    {
      // 4 bytes for header + payload
      ByteBuffer buffer = ByteBuffer.allocate(2 + 2 + payload.length());
      // we set that we want big endian numbers
      buffer.order(ByteOrder.BIG_ENDIAN);
    
      buffer.putShort((short)magicNumber);
      buffer.putShort((short)payload.length());
      buffer.put(payload.getBytes("US-ASCII"));
      return buffer.array();
    }
    
    public static void main (String[] args) throws java.lang.Exception
    {
        try
        {
            byte[] bytes = buildPacket(0xFF10, "foobar");
            for (byte b : bytes)
              System.out.printf("0x%02X ", b);
        }
        catch (Exception e)
        {
            e.printStackTrace();
        }
    }
    

    请注意,如果您声明该方法直接接受 short 幻数,您将无法传递文字幻数 > 32767,因为 short 是用 Java 签名的。

    【讨论】:

    【解决方案2】:

    在`Socket.getOutputStream() 周围使用BufferedOutputStream 周围的DataOutputStream。然后你可以使用:

    • writeShort() 为幻数
    • writeShort() 为长度字
    • write() 用于有效负载。

    同样,您可以使用DataInputStream 和相应的readXXX() 方法来读取响应。

    注意,您在这里写入的是套接字,而不是服务器套接字。

    【讨论】:

      【解决方案3】:

      提防大尾端!

      DataxxxStream - 虽然非常方便 - 不完全支持小端和大端数字以及任意字符串编码。

      How to Read Byte Stream from Socket查看我的帖子

      【讨论】:

      • 该问题明确指定了大端字节序。
      • EJP,我尊重你的回答。我想知道你为什么忽略那些 DataXxxxStream 不是解决方案的边缘情况,例如小端数据和两个单独问题中的非 utf8 字符串编码?!
      猜你喜欢
      • 1970-01-01
      • 2016-04-24
      • 2016-09-01
      • 2021-06-24
      • 1970-01-01
      • 1970-01-01
      • 2011-01-29
      • 2021-12-15
      • 2021-09-23
      相关资源
      最近更新 更多