【问题标题】:Please tell me what is wrong with my threading!请告诉我我的线程有什么问题!
【发布时间】:2010-05-11 08:07:32
【问题描述】:

我有一个函数可以将一堆文件压缩成一个压缩文件..它需要很长时间(压缩),所以我尝试在我的应用程序中实现线程..假设我有 20 个文件压缩,我将其分隔为 5*4=20,为了做到这一点,我对所有 4 个线程都有单独的变量(用于压缩)以避免锁定,我将等到 4 个线程完成..现在..线程正在工作,但我看不到它们的性能有所改善。通常在实现线程之后需要 1 分钟来处理 20 个文件(例如)...只有 5 或 3 秒的差异。有时是相同的。 这里我将展示 1 个线程的代码(其他 3 个线程也是如此)

//main thread   
    myClassObject->thread1 = AfxBeginThread((AFX_THREADPROC)MyThreadFunction1,myClassObject);
    ....

    HANDLE threadHandles[4];
    threadHandles[0] = myClassObject->thread1->m_hThread;
    ....

    WaitForSingleObject(myClassObject->thread1->m_hThread,INFINITE);

UINT MyThreadFunction(LPARAM lparam)
{

    CMerger* myClassObject = (CMerger*)lparam;
    CString outputPath = myClassObject->compressedFilePath.GetAt(0);//contains the o/p path
    wchar_t* compressInputData[] = {myClassObject->thread1outPath,
                    COMPRESS,(wchar_t*)(LPCTSTR)(outputPath)};
    HINSTANCE loadmyDll;
    loadmydll = LoadLibrary(myClassObject->thread1outPath);
    fp_Decompress callCompressAction = NULL;
    int getCompressResult=0;
    myClassObject->MyCompressFunction(compressInputData,loadClient7zdll,callCompressAction,myClassObject->thread1outPath,
                    getCompressResult,minIndex,myClassObject->firstThread,myClassObject);
    return 0;
}

【问题讨论】:

  • 你确认压缩的瓶颈是CPU,你真的有多个内核可用吗?如果瓶颈是文件系统,那么让更多的线程来完成这项工作并没有什么不同。

标签: multithreading mfc


【解决方案1】:

首先,您只等待其中一个线程。我想你想要 WaitForMultipleObjects。

至于缺乏加速,您是否认为您的实际瓶颈不是压缩而是文件加载?文件加载速度很慢,4 个线程争用硬盘的时间片“甚至可能”导致性能下降。

这就是为什么过早优化是邪恶的。您需要再次分析、分析和分析,以找出真正的瓶颈在哪里。

编辑:除非我看到代码,否则我无法真正评论您的 WaitForMultipleObjects。我自己从来没有遇到过任何问题......

至于瓶颈。这是一个比喻,如果你试图通过倒置来将大量液体从圆柱体中倒出,然后水以恒定的速度离开。如果你尝试用瓶子来做这件事,你会发现它做不到那么快。这是因为只有这么多的液体可以流过瓶子的薄部分(更不用说进入它的空气了)。因此,从容器中排空水的限制受到瓶颈(较薄的部分)的限制。

在编程中,当您谈论瓶颈时,您指的是代码中最慢的部分。在这种情况下,如果您的线程大部分时间都在等待磁盘加载完成,那么您将通过多线程获得很少的速度,因为您一次只能加载这么多。事实上,当您尝试一次加载 4 倍的内容时,您会开始发现您必须等待同样长的时间才能完成加载。在您的单线程情况下,您等待并在加载后进行压缩。在 4 线程的情况下,您等待所有加载完成的时间大约是 4 倍,然后您同时压缩所有 4 个文件。这就是为什么你得到一个小的加速。不幸的是,由于您花费大部分时间等待加载完成,您将看不到任何接近 4 倍速度的东西。因此,您的方法的限制因素不是压缩,而是从磁盘加载文件,因此它被称为瓶颈。

Edit2:在您建议的情况下,您会发现通过消除等待从磁盘加载数据的时间量可以获得最佳速度。

1) 如果您将文件加载为多个磁盘页面(通常为 2048 字节,但您可以查询窗口以获取大小),您将获得最佳的加载性能。如果你加载的大小不是这个的倍数,你会受到相当严重的性能影响。

2) 查看异步加载。例如,您可以在处理文件 1 时将所有文件 2(或更多)加载到内存中。这意味着您无需等待加载完成。但是,它不太可能在这里获得巨大的速度,因为您最终可能仍会等待负载。要尝试的另一件事是异步加载音频文件的“块”。即:

  • 加载区块 1。
  • 开始加载区块 2。
  • 处理块 1.
  • 等待区块 2 加载。
  • 开始加载区块 3。
  • 处理块 2。
  • (等等)

3) 你可以买一个更快的磁盘驱动器。

【讨论】:

  • 是的,看起来 I/O 更像是瓶颈。
  • 又是你 Goz,希望你能告诉我一个方法....Goz 问题是我对压缩代码了解不多(它是另一个 dll,但它的线程安全)。我我正在等待所有 4 个线程..我在示例中只显示了一个。我尝试使用 WaitfotmultopleObjects 但它没有等待最后一个线程完成..它就像第 4 个线程在等待之后运行 n 这就是为什么我使用等待单
  • 也不确定你们为什么使用“瓶颈”这个词..这对我的情况意味着什么..请解释
  • 所以,在任何文件处理的情况下......我们如何提高性能......不会有多线程吗?或任何其他方法
猜你喜欢
  • 2016-03-09
  • 1970-01-01
  • 1970-01-01
  • 2022-06-15
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2023-03-30
  • 2023-01-14
相关资源
最近更新 更多