【问题标题】:Java Client/Server File transfer with Multithreading Problem具有多线程问题的 Java 客户端/服务器文件传输
【发布时间】:2025-12-07 02:45:02
【问题描述】:

我想创建简单的下载加速器。

它是如何工作的

  1. 服务器等待传入连接。
  2. 客户端连接到服务器。
  3. 然后,服务器将文件大小发送给客户端并等待下载连接。
  4. 客户端获取文件大小,然后创建下载线程,这些线程连接到服务器。
  5. 服务器从每个线程获得连接后,服务器将等待来自线程的开始和结束偏移文件。
  6. 每个线程将开始和结束偏移文件发送到服务器。
  7. 服务器获得偏移后,服务器会将文件的一部分发送到线程。
  8. 每个线程都会读写文件。例如buffer.p01、buffer.p02、buffer.p03
  9. 客户端按顺序将所有文件合并为一个文件。 (尚未实施

我认为服务器端它工作正常,但客户端它有一些问题。

问题是如果我将 MAXTHREAD 设置为 1,它可以正常工作。但如果我设置了多个,它就会永远卡在某个地方。

这是服务器端代码.. http://pastebin.com/TEakGB0c

这是带有多线程的客户端代码 http://pastebin.com/wKhP7DxS

谢谢你。

【问题讨论】:

  • 听起来像是一个死锁问题。没有任何代码,我们真的无法提供帮助吗?
  • 我已经在问题的末尾发布了代码。你能看到吗?
  • 啊,我现在明白了。让我看看。
  • @Atom,如果您想增加带宽份额,拥有多个连接会有所帮助。如果所有客户端具有相同数量的连接,它们的执行将完全相同。
  • @Peter 我不明白@_@。你能给我举个例子吗?

标签: java multithreading sockets client-server


【解决方案1】:

你有一个非常明显的问题。 ServerSocket 的 accept 方法每次都会返回一个新的套接字。在您的服务器代码中

initSocket = servSock.accept();

initSocket 是一个类成员字段,这意味着您将覆盖旧套接字并且永远不会关闭它。您应该启动一个新线程来处理此套接字,从我看来,您似乎只是继续重用同一个套接字。那是行不通的。查看有关如何打开套接字的教程。抱歉,我帮不上忙,但这里发生了很多事情,但这些事情是行不通的。也许您可以开始关注部分代码,我们可以提供更多帮助。

【讨论】:

    【解决方案2】:

    我同意,这可能是一个小问题,也可能是一个大问题,一些示例代码将帮助我们帮助您,如果您尝试使用同一端口连接到服务器 3 次,您将收到错误,因为您每个端口只能有 1 个连接,问题可能非常简单或非常复杂,如果您编辑帖子并添加代码,那么我们可以更好地帮助您。

    【讨论】:

      【解决方案3】:
      Please close your OutputStream os 
      
      Sending u a snippet
      
      
      public static boolean sendFile() {
              int start = Integer.parseInt(startAndEnd[0]) - 1;
              int end = Integer.parseInt(startAndEnd[1]) - 1;
              int size = (end - start) + 1;
              try {
                  os = initSocket.getOutputStream();
                  os.write(byteArr, start, size);
                  os.flush();
                  System.out.println("Send file to : " + initSocket);
              } catch (IOException e) {
                  System.out.println(e.getLocalizedMessage());
                  disconnected();
                  return false;
              } finally {
                  if (os != null) {
                      try {
                          os.close();
                      } catch (IOException ex) {
                          Logger.getLogger(FileServer.class.getName()).log(Level.SEVERE, null, ex);
                      }
                  }
              }
              return true;
          }
      

      【讨论】: