0

嘿伙计们,我一直在尝试制作 NIO 服务器/客户端程序。我的问题是服务器只发送 14 个字节然后它不会再发送任何东西。我已经坐了很长时间,以至于我真的什么都看不到了,因此决定看看这里是否有人能看到问题

服务器代码:

import java.nio.*;
import java.nio.channels.*;
import java.nio.charset.*;

public class Testserver {
    public static void main(String[] args) throws java.io.IOException {

        ServerSocketChannel server = ServerSocketChannel.open();
        server.socket().bind(new java.net.InetSocketAddress(8888));

        for(;;) { 
            // Wait for a client to connect
            SocketChannel client = server.accept();  

            String file = ("C:\\ftp\\pic.png");


            ByteBuffer buf = ByteBuffer.allocate(1024);
            while(client.read(buf) != -1){

            buf.clear();
            buf.put(file.getBytes());
            buf.flip();

            client.write(buf);
            // Disconnect from the client
            }
            client.close();
        }
    }
}

客户:

import java.io.IOException;
import java.net.InetSocketAddress;
import java.nio.ByteBuffer;
import java.nio.channels.Channels;
import java.nio.channels.ReadableByteChannel;
import java.nio.channels.SocketChannel;
import java.nio.channels.WritableByteChannel;
import java.io.*;
import java.net.*;
import java.nio.*;
import java.nio.channels.*;
import java.nio.charset.*;
public class Testclient {

    public static void main(String[] args) throws IOException {



        SocketChannel socket = SocketChannel.open(new InetSocketAddress(8888));



        FileOutputStream out = new FileOutputStream("C:\\taemot\\picNIO.png");
        FileChannel file = out.getChannel();

        ByteBuffer buffer = ByteBuffer.allocateDirect(8192);

        while(socket.read(buffer) != -1) { 
          buffer.flip();       
          file.write(buffer); 
          buffer.compact();    
          buffer.clear();
        }
        socket.close();        
        file.close();         
        out.close();           
    }
}
4

1 回答 1

0
  1. 您只发送文件名,而不是文件内容。文件名是 14 个字节。

  2. 每次客户端发送任何内容时,您都会发送它。但是客户端从来没有发送任何东西,所以我很惊讶你甚至得到了 14 个字节。

  3. 您忽略了 write() 的结果。

如果要发送文件内容,请使用 FileChannel 打开它。同样,在客户端中使用 FileChannel 打开目标文件。然后复制循环在两个地方都是一样的。在通道之间复制缓冲区的正确方法如下:

while (in.read(buffer) >= 0 || buffer.position() > 0)
{
  buffer.flip();
  out.write(buffer);
  buffer.compact();
}

请注意,这会处理部分读取、部分写入和读取 EOS 后的最终写入。

说了这么多,我看不出有任何理由在这里使用 NIO。使用 java.net 套接字和 java.io 流会简单得多。

于 2012-10-24T23:20:16.993 回答