【问题标题】:Multithreading takes more time than Sequential Execution in C#多线程比 C# 中的顺序执行花费更多时间
【发布时间】:2012-08-03 15:23:34
【问题描述】:

我在我的 while 循环中使用多线程, 作为

while(reader.read())
{
 string Number= (reader["Num"] != DBNull.Value) ? reader["Num"].ToString() : string.Empty;
  threadarray[RowCount] = new Thread(() =>
  {

  object ID= (from r in Datasetds.Tables[0].AsEnumerable()
                                            where r.Field<string>("Num") == Number
                                            select r.Field<int>("ID")).First<int>();


 });

                threadarray[RowCount].Start();
                RowCount++;
}

但是对于 200 个阅读器来说,顺序执行只需要 0.4 秒 但是使用线程需要 1.1 秒...这是一个示例,但是当我在多个数据库操作的线程中使用多行代码执行它时,我遇到了同样的问题。

对于顺序,它需要 10 秒,对于线程,它需要更多...

谁能推荐我?

谢谢...

【问题讨论】:

  • 建议什么?如您所见,线程和同步有开销。
  • 你是怎么多线程的呢?线程不是免费的,也许你并行运行了太多东西并导致线程饥饿。
  • 您在线程中执行的内容似乎也没有变化,或者我错过了什么?建议依次做。好像更快了……
  • 建议你阅读这篇文章。关于多线程性能的精彩文章msdn.microsoft.com/en-us/library/ms810437.aspx
  • 粘贴您的普通(非线程)代码? ...只是一些猜测:线程有一个开销,并且很明显你的任务太小了,以至于开销被证明对性能不利。您还在为每件事创建新线程(在给定时间只能在机器上运行有限数量的线程。线程池可能会提高性能)。

标签: c# multithreading


【解决方案1】:

线程并不总是更快,在许多情况下可能会更慢(例如这里看到的情况)。原因有很多,但最重要的两个是

  • 创建线程是一项相对昂贵的操作系统操作
  • 上下文切换(CPU 停止在一个线程上工作并开始在另一个线程上工作)再次是一项相对昂贵的操作

创建 200 个线程将花费相当多的时间(使用默认堆栈大小,这将为堆栈单独分配 200MB 内存),除非您有一台具有 200 个内核的机器,否则操作系统还需要花费相当多的时间这些线程之间的时间上下文切换也是如此。

最终结果是机器花费在创建线程和在它们之间切换的时间远远超过机器花费在任何工作上的时间。如果减少正在使用的线程数,您可能会看到性能改进。尝试为您机器的每个内核使用 1 个线程。

线程数多于内核数的多线程通常仅在 CPU 等待事件发生(如磁盘 IO 或网络通信)的情况下才有用。这不是这里的情况。

【讨论】:

    【解决方案2】:

    线程并不总是解决方案,而且您使用它的方式绝对不是线程安全的。在某些情况下,诸如磁盘 I/O 或其他瓶颈之类的事情不会从线程中受益。

    此外,启动线程是有成本的。并不是说我会根据您的情况推荐它,但请查看 TPL。 http://msdn.microsoft.com/en-us/library/dd460717.aspx

    【讨论】:

      【解决方案3】:

      多线程通常是非阻塞执行的选择。就像地球上的一切事物一样,它也有相关的成本。

      对于并行执行的商品,我们以性能为代价。

      通常没有什么比顺序执行单个任务更快的了。

      在你的具体场景中,很难提出真实的东西。

      也许你可以考虑多个进程执行,而不是多个线程执行。

      但我重申,如果不了解应用程序的完整架构和要求,很难判断您是否会从中受益。

      【讨论】:

        【解决方案4】:

        您似乎正在为每个 read() 创建一个线程。因此,如果它有 200 个 read(),则您有 200 个线程正在运行(可能会更少,因为有些线程可能会很快完成)。取决于您在线程中执行的操作,同时运行 200 个线程实际上可能会因为其他人提到的开销而减慢系统速度。

        multithread 在 1) 线程中的工作需要一些时间才能完成时为您提供帮助; 2)您可以控制同时运行的线程数。

        在你的情况下,你需要尝试,比如 10 个线程。如果有 10 个线程正在运行,则等待其中 1 个完成,然后将线程分配给新的 read()。

        如果线程中的作业不需要太多时间,那么最好使用单线程。

        【讨论】:

          【解决方案5】:

          科幻作家和技术专家 Jerry Pournelle 曾经说过,在理想世界中,每个流程都应该有自己的处理器。这不是一个理想的世界,您的机器可能有 1 - 4 个处理器。即使您自己在做白日梦,您的 Windows 系统本身也正在运行大量进程。我刚刚统计了我的 Core 2 Quad XP 机器上运行的进程,而 SYSTEM 正在运行 65 个进程。那是必须在 4 个处理器之间共享的 65 个进程。添加更多线程,每个线程只能获得一部分处理器能力。

          如果您有Beowulf Cluster,您可以将线程共享到单独的机器中,您可能会得到非常好的时机。但是您的机器仅使用 4 个处理器无法做到这一点。你要求它做的越多,性能就会越差。

          【讨论】:

            猜你喜欢
            • 1970-01-01
            • 1970-01-01
            • 2021-11-01
            • 1970-01-01
            • 1970-01-01
            • 2014-04-23
            • 1970-01-01
            • 1970-01-01
            • 2020-12-10
            相关资源
            最近更新 更多