我用DataOutputStream的write(byte[])向流中写了几个byte,又用writeLong(long)写了 一个数。然后依次用DataInputStream的read(byte[]),readLong()可以正确读出来数据。
  我一直不太明白在底层是如何把byte和long区分开的,在流中,byte和long不都变成二进制了吗,为什么read(byte[])时候不把long这个数也当作byte给读出来?有哪位达人给讲一下?

解决方案 »

  1.   

    用write(byte[])的时候,所传递的参数会告诉这个函数往里面写多少个byte;而用read(byte[])的时候,也应当指定读多少个byte,否则会出错的。请看下例:import java.io.DataInputStream;
    import java.io.DataOutputStream;
    import java.io.File;
    import java.io.FileInputStream;
    import java.io.FileOutputStream;
    import java.io.IOException;public class Test {    public static void main(String[] args) throws IOException {
            File f = new File("D:\\a.txt");
            
            DataOutputStream dos = new DataOutputStream(new FileOutputStream(f));
            byte[] ba = new byte[1];
            ba[0] = (byte) 1;
            dos.write(ba); //这里数组ba的长度为1,也就是说,只往文件里写一个byte
            dos.writeLong((long)2);
            dos.close();
            
            DataInputStream dis = new DataInputStream(new FileInputStream(f));
            byte[] bb = new byte[2];
            dis.read(bb); //这里bb长度为2,也就是说要读两个byte
            for (int i = 0; i < bb.length; i++) {
                System.out.println(bb[i]);
            }
            long l = dis.readLong();
            System.out.println(l);
            dis.close();
        }
    }以上的代码是先往文件里写一个byte,再写一个long;读的时候是读两个byte,再读一个long。这样问题就来了:由于多读了一个byte,在读long的时候还没有读完就遇到文件结尾了,所以会抛出java.io.EOFException不知楼主是否明白了?
      

  2.   

    byte和long不都变成二进制了吗,为什么read(byte[])时候不把long这个数也当作byte给读出来?
    ====================================================
    我的理解是long与byte其实是互通的,只是1个long=n个byte. 具体是多少个bit(位)可以能过Long.SIZE 静态变量查看到. 你用一句writeLong(long)应该是等于write(byte[n])的. 你不防可以自己写程序测试一下.
      

  3.   

    1个long 应该 = Long.Size/8 个byte 吧.
      

  4.   

    具体格式我没研究过,感兴趣的话你可以看看Data是如何读如何写的。
    但是道理是显然的,写一个byte和一个long,而读两个byte,一个long,显然读的第二个byte要读取long的一部分了,所以再读long就出错了。
      

  5.   

    感谢brooksychen(初晨之阳) 和lzheng2001(1加1),你们说的在普通的IO流中确实是正确的。
    但我用Socket流试了一下,却更让我迷惑了
    -----------------服务器端-------------
    public class Server2 { public static void main(String[] args) {
    try {
    ServerSocket server=new ServerSocket(9999);
    Socket socket=server.accept();
    DataInputStream input=new DataInputStream(socket.getInputStream());
    byte [] buffer=new byte[1024];
    input.read(buffer);
    System.out.println(new String(buffer,"ASCII"));
    System.out.println(input.readLong());
    System.out.println(input.read());
    } catch (Exception e) {

    e.printStackTrace();
    }
    }}
    ----------------客户端----------------
    public class Client2 { public static void main(String[] args) {
    try {
    Socket client=new Socket("localhost",9999);
    DataOutputStream output=new DataOutputStream(client.getOutputStream());
    String str="hello";
    output.write(str.getBytes("ASCII"));
    output.writeLong((long)2);

    output.flush();
    output.close();
    } catch (Exception e) {
    e.printStackTrace();
    }
    }}
    ---------------------------------
    运行结果正确,服务端尝试读1024个比特,为什么不把long也当作字符给读进去,而能区别开?
    我非常疑惑。