1

目前,我的服务器程序能够从客户端套接字接收文件,并能够将接收到的文件保存在服务器机器中。但是我需要从客户端套接字到服务器套接字接收许多文件,而无需每次都关闭和打开套接字连接。

我已经编写了代码,这工作正常。但是在这个我在每次迭代中关闭和打开服务器和客户端套接字连接。但是我需要这样做而不是每次都连接和断开两个套接字。

请各位前辈指点...


我的服务器代码:

        int img_count=1;
        int bytesRead;
        int current = 0;
        byte [] mybytearray  = new byte [100000];

        InputStream is = null;
        FileOutputStream fos = null;
        BufferedOutputStream bos = null;
        Socket sock=null;

        // create socket
        ServerSocket servsock = new ServerSocket(6668);
        System.out.println("Waiting... for client req");
        int i=0;


         for ( i=0; i<9; i++)
          {

              sock = servsock.accept();        // Waiting for Client

              String fname = "Image000"+(img_count++)+".JPG";
              String fpath = "C:/RX_images/"+fname;      // Image saving path
              File myFile = new File (fpath);

              is = sock.getInputStream(); 
              fos = new FileOutputStream(myFile);
              bos = new BufferedOutputStream(fos);
              bytesRead = is.read(mybytearray,0,mybytearray.length);
              current = bytesRead;

           do {
              bytesRead =
              is.read(mybytearray, current, (mybytearray.length-current));
              if(bytesRead >= 0) current += bytesRead;
            } while(bytesRead > -1);

              bos.write(mybytearray, 0 , current);

              bos.flush();
              fos.flush();
              fos.close();
              bos.close();
              is.close();
              sock.close();

          }  // End of for loop

          servsock.close();
          System.out.println("Received : "+ (i++)+ " Images");

我的客户代码:

        int i=0;  
        int img_count=1;
        FileInputStream fis=null;
        BufferedInputStream bis=null;
        OutputStream os=null;
        Socket client=null;

        System.out.println("Sending...");


      for ( i=0; i<9; i++)
      {
          client = new Socket("192.168.1.54",6668);    

          String fname = "Image000"+(img_count++)+".JPG";
          String fpath = "C:/Tx_Images/"+fname;          // Image path
          File myFile = new File (fpath);

          byte [] mybytearray  = new byte [(int)myFile.length()];

          fis = new FileInputStream(myFile);
          bis = new BufferedInputStream(fis);        
          bis.read(mybytearray,0,mybytearray.length);
          os = client.getOutputStream();        
          os.write(mybytearray,0,mybytearray.length);

          bis.close();
          fis.close();
          os.flush();
          os.close();
          client.close();
          Thread.sleep(2000); 

      }   // End of for loop

      System.out.println("\n Sent : "+(i++)+" Images");

我对java很陌生,请帮助我....

4

3 回答 3

0

由于套接字只是一个字节流,为了处理多个文件,您将不得不构建某种简单的协议。换句话说,发送者必须发送区分一个文件中的字节和另一个文件中的字节的字节。由于您正在发送二进制数据,因此您无法发送一系列字节来“标记”开始和/或/结束 - 例如,如果您在末尾发送 4 个零字节,那可能是数据,因此接收器不能确定它是标记还是数据。临时想到了两种处理它的方法——将文件分成最多 N 个字节的部分,然后一次发送一个部分。您必须计算每个部分中的字节数,因为至少一个部分的字节数不会与所有其他部分相同。交替,y 您可以计算文件中的字节数并从给出该计数的字节开始,因此接收者知道预期有多少字节。在提供计数时,如果需要,您还可以提供文件名称和类型等信息。祝你好运。

于 2013-01-13T15:12:02.553 回答
0

这个问题实际上取决于您是否需要客户端保持连接打开。通常你只需要保持服务器端的监听,客户端每次需要发送文件时重新连接就可以了。

使用 anExecutorService来保持服务器端运行并使用单独的线程处理多个连接。然后让客户端连接并发送它需要发送和断开连接的内容。请参阅此问题以获取快速示例:多线程套接字通信客户端/服务器

另外,看看他们如何关闭资源(最终)并在该示例中停止服务器。这与您的问题无关,但您也希望使您的 I/O 和错误处理更加健壮。

如果您确实需要服务器和客户端保持连接并发送多个文件(或任何数据),那么您需要像 rcook 笔记那样实现某种协议,并且您需要更深入地了解网络并拥有一个心跳之类的。而且,即使你这样做了,客户端仍然需要足够聪明,以便在套接字关闭等情况下尝试重新连接。

于 2013-01-13T16:03:22.990 回答
0

只需制作简单的协议,例如:

 File Name\r\n
 File Size\r\n
 File Data\r\n
 File Name\r\n
 File Size\r\n
 File Data\r\n
 ....

我希望你会明白这一点。您可以先发送文件信息,然后服务器将解析此文件信息,并使您的服务器读取您在文件信息中指定的字节数。这些将使您能够查看文件结束标记以及何时开始新文件。但是您必须事先知道文件大小。

这不适用于长度未知的数据流。

让您的服务器读取您将指定的字节数,以便服务器可以知道何时结束文件写入并开始新文件,或者在套接字关闭之前文件是否已完全接收......

于 2013-01-13T17:38:19.930 回答