代码之家  ›  专栏  ›  技术社区  ›  thr

对大量文件之间的大量数据使用最快的套接字方法

  •  4
  • thr  · 技术社区  · 15 年前

    我正在构建一个socket应用程序,它需要将许多中小型文件(比如5-100kb大小的文件)转移到许多不同的客户机(有点像Web服务器,但仍然不完全是这样)。

    我应该在winsock(win32)中使用标准的poll/epoll(linux)或异步套接字,还是有性能更高的方法(例如win32上的重叠I/O)?

    Linux和Windows都是可能的平台!

    6 回复  |  直到 15 年前
        1
  •  1
  •   Pawel Marciniak    15 年前

    在Windows上,您可以尝试使用 TransmitFile 这有可能通过避免内核空间<->用户空间数据复制来提高性能。

        2
  •  3
  •   Charles Salvia    15 年前

    在Linux上,使用 epoll 是通过TCP进行并行I/O的最快方法。

    但我也会提到,为了便于移植,(既然您似乎对Linux或Windows感兴趣),您应该研究boost.asio。它有一个可移植的API,但是使用 埃波尔 在Linux上,在Windows上重叠I/O,因此您可以构建高效的 便携式网络应用程序。

    此外,由于您使用的是文件,因此在执行I/O时还应该实现双缓冲以获得最大性能。换句话说,您使用两个缓冲区发送/接收每个文件。例如,在发送端,您将从磁盘读取到一个缓冲区,然后通过网络发送该缓冲区,而另一个线程将下一个数据块从磁盘读取到第二个缓冲区。这样就可以将磁盘I/O与网络I/O重叠。

        3
  •  2
  •   caf    15 年前

    在Linux上, sendfile() 是专门用于将数据从文件发送到套接字的高性能API(您仍需要使用 poll 对于多路复用,它只是 read / write 部分)。

        4
  •  2
  •   Nikolai Fetissov    15 年前

    除了 epoll 它看起来像Linux sendfile(2) 很适合您在服务器端的需求。

        5
  •  0
  •   Community CDub    8 年前

    不幸的是,如果您希望尽可能提高性能,您仍然需要在Windows和Linux上手工编写I/O代码,因为当前可用的抽象库不能很好地扩展到多个线程(如果有的话)。

    如果您想要可移植性(和易用性),Boost ASIO可能是最好的选择,但在多线程可伸缩性方面它确实有其局限性(请参见 C++ Socket Server - Unable to saturate CPU )-我想主要的问题是在不过度锁定的情况下将超时处理集成到多线程事件循环中。

    从本质上讲,您想要使用的最大性能是I/O完成端口(Windows上有一个工作线程池)和边缘触发的epoll(Linux上有一个工作线程池)。

        6
  •  0
  •   MarkR    15 年前

    不要过早地优化程序。

    假设这不是一个过早的优化,最简单的事情就是将所有数据保存在内存中。如果愿意,您可以mmap()它们,或者在启动时加载它们。发送已经在记忆中的东西是一件很简单的事情。

    说了这句话,尝试用epoll复用很多东西可能会有点头疼,难道你不能用别人已经写过的东西吗?