在现代的操作系统和硬件环境中,应用程序的执行速度往往受限于多线程处理的能力。本文将探讨如何通过多线程技术来优化应用程序的执行速度。作者通过实验和调整,发现了提高程序性能的有效方法,并分享了在此过程中的发现和结论。
为了提升应用程序的执行速度,作者选择了从最基础的层面——即执行速度最慢但代码最简单的部分——开始优化。通过逐步增加代码的复杂性,同时保持稳定的操作基础,作者开始了对多线程处理的探索。
最初,作者采用了一种原始的方法来处理每一个步骤:从网络服务器下载JSON数据,解析需要的数据元素,并最终显示这些数据。然而,这种方法很快就显示出处理时间远非最优。
在初步编码完成后,作者发现,由于下载过程的瓶颈,应用程序需要等待7到10秒才能显示数据,而浏览器仅需大约1秒。作者意识到,下载过程本身是最大的瓶颈,因为需要下载的数据通常超过5MB,而主线程在等待服务器传输数据时大部分时间处于空闲状态。
为了解决这个问题,作者决定将下载的数据块大小从1MB减少到16,384字节。这样,应用程序就只需要等待16k的单个数据块,而不是等待5MB以上的数据全部下载完成。
作者实现了一个处理JSON数据中元素分隔的流程,考虑到每个元素可能会在16k的数据块之间分割,并且一个16k的数据块可能包含多个元素。一旦元素完全存在于内存中,就会创建新的工作线程来处理它们。
作者尽量避免使用Windows平台的同步机制,如互斥锁(mutex),因为它们既复杂又效率未知。相反,作者采用了一种更简单的方法,所有下载的数据都存储在一个全局内存块中。作者通过传递一个指向目标元素和其大小的指针对,来简化线程间的通信。
在执行过程中,作者意外地发现了“最大线程数”问题。由于同时执行的线程太多,作者遇到了Windows平台对每个进程10,000个GDI句柄的限制。为了解决这个问题,作者开始逐步降低最大并发线程数,直到GDI句柄问题消失。
通过创建一个高速校准过程,作者测试了不同数量的并发测试线程的执行时间,最终确定了最优的线程数量。在作者的测试系统中,最优的线程数是16,这与作者的i9 9900k处理器的核心数相匹配。
通过实验和调整,作者发现,对于大约400个需要单独处理的元素的大型文件下载,通过多线程优化可以显著节省时间。最终,应用程序的执行速度比最初编码时快了大约10倍。
尽管有人认为确定最优的线程数量和实施队列系统来尊重这个最大值可能是过度的,但考虑到需要单独处理的元素数量,这种努力是值得的。
作者建议,通过从概念上审视应用程序的行为,量化、总结和观察,识别空闲点和瓶颈,并创造性地让CPU在这些时间里做一些有建设性的工作,可以显著提高应用程序的性能。
本文通过作者的亲身经历,展示了如何通过多线程技术优化应用程序的执行速度。作者不仅分享了在优化过程中的发现,还提供了一种方法来确定最优的线程数量,并通过实施队列系统来管理线程,从而显著提高了应用程序的性能。