线程示例C#

时间:2011-12-19 12:24:01

标签: c# multithreading

我在互联网上找到了这本书。约瑟夫在C#中穿线我试过它的例子

class ThreadTest
{
    static void Main()
    {
        Thread t = new Thread(WriteY);          // Kick off a new thread
        t.Start();                               // running WriteY()

        // Simultaneously, do something on the main thread.
        for (int i = 0; i < 10000000; i++) Console.Write("x");
        Console.ReadLine();
    }
    static void WriteY()
    {
        for (int i = 0; i < 10000000; i++) Console.Write("y");
    }
}

问题是,当我运行这个程序时(我在for循环中给出更高的值来观察)我的cpu利用率坚持100%。我不想要这个,我的意思是,无论如何要减少使这个程序减少cpu密集度?我刚接触多线程概念,所以我想我应该事先询问。

7 个答案:

答案 0 :(得分:8)

如果您可以同时使用多个资源,则多线程可以改善您的应用程序。 例如,如果您有多个核心或多个CPU,我相信上面的示例应该会更好。

或者,如果您有一个使用CPU的线程,以及另一个同时使用该磁盘的线程,如果您使用多线程,它也会表现得更好。

但是,如果您有一个CPU或一个核心,则上述示例将无法更好地执行。它会表现得更糟。

答案 1 :(得分:5)

你无法降低利用率,因为你使用的是两个线程(很可能是在双核上),这两个线程都是工作密集型的(它们循环并打印一些东西)。也许减少线程优先级可能有所帮助,但我认为这不是这个例子的重点。

答案 2 :(得分:5)

WriteY函数中的循环将尽快执行。所以它将使用100%的CPU。如果您希望它的资源消耗较少,那么您可以做两件事:

  • 更改线程的优先级。这样,您的应用程序仍将使用100%的CPU,但如果另一个线程需要CPU资源,该线程将“减速”

  • 在WriteY函数中添加一个暂停:

    static void WriteY()
    {
        for (int i = 0; i < 10000000; i++)
        { 
            Console.Write("y");
            Thread.Sleep(100);
        }
    }
    

答案 3 :(得分:2)

Thread.Sleep(num of millseconds)之后添加Console.Write因为循环将完全利用cpu。

class ThreadTest 
{
     static void Main()
     {
         Thread t = new Thread(WriteY);
          // Kick off a new thread
         t.Start();
         // running WriteY()
         // Simultaneously, do something on the main thread.
         for (int i = 0; i < 10000000; i++)
         {
              Console.Write("x");
              Console.ReadLine();     
         }
     }     

    static void WriteY()
    {
         for (int i = 0; i < 10000000; i++) 
         {
               Console.Write("y");
               Thread.Sleep(1000); // let the thread `sleep` for one seconds before running.     
         } 
    } 
}

<强>更新

好吧,你可以使用This example,使用.Net 4 Parallel Extensions,以防你有多个核心。

var result = from ipaddress in new[]
{
  "111.11.11.11",
  "22.22.22.22",
  "22.33.44.55"
  /* or pulled from whatever source */
}
.AsParallel().WithDegreeOfParallelism(6)
let p = new Ping().Send(IPAddress.Parse(ipaddress))
select new
{
  site,
  Result = p.Status,
  Time = p.RoundtripTime
}

/* process the information you got*/

答案 4 :(得分:0)

改变这个:

for (int i = 0; i < 10000000; i++) Console.Write("x");

进入此代码:

for (int i = 0; i < 10000000; i++) 
    {
       Console.Write("x");
       Thread.Sleep(5);
    }

答案 5 :(得分:0)

我读到您的处理器可以处理的活动有两种主要的不同类型。我可能在这些语句中有错误的措辞/语法,如果有人可以纠正语法,我将不胜感激。

  1. 计算工作(计算限制):向处理器提供纯计算任务,处理器可在其上工作,无需外部设备或组件的任何输入。

  2. 基于输入的工作(I / O界限):当您的处理器正在处理某些事情时,还需要读取或写入某些内容,或者需要等待网络活动。例如,从磁盘读取文件或下载文件。

  3. 它们之间的主要区别在于计算应该在没有等待的情况下使用,以便在尽可能最快的时间内完成任务。 例如:

    for(int i = 0; i<= 10000; i++)
    {
    
    }
    

    没有与系统中任何“慢”部分的交互,所以对于这样的事情,你不介意计算/计算耗尽cpu,因为它可能无论如何都要在微秒的空间内完成。 / p>

    这对于挖掘比特币或强制组合等特别重要。

    你不会为这些添加'睡眠',因为它会不必要地减慢你的速度。

    但是,如果您的工作负载是基于输入的,则需要读取或写入硬盘驱动器或网络;与纯数学工作相比,被认为速度较慢的活动,然后添加Thread.Sleep(x)并不是一件坏事,因为有时你的硬盘驱动器/ Ram产生数据的速度并不像你的处理器那么快。

    线程在这两个不同主题中特别有趣, 对于计算工作,您希望线程在100%不间断运行一段时间,那么最好不要超过线程计数中的处理器计数。

    例如:Environment.ProcessorCount

    事实上,我几乎建议使用Environment.ProcessorCount -1的线程计数(在双核或更高的情况下) 使用100%的所有核心/处理器可能导致线程锁定,这实际上会阻碍性能。

    我对此进行了实验,发现在双核系统上,我可以使用单核完成更多循环/迭代,而不是完全使用两个核。

    如果我使用的是四核,我发现通过使用3对全部4可以获得更多。

    (不要忘记,其中一个处理器必须共享操作系统功能,以及渲染窗体应用程序GUI - 如果有的话)

    但是,如果您正在开发一个使用基于输入的计算的应用程序,它需要与许多慢速设备或依赖项进行交互,那么超出处理器数量可能不是一件坏事。

    例如:如果每个线程中都有很多thread.sleeps,那么您可以策略性地规划线程休眠,而其他线程可以工作。

    我过去使用多线程实验室监视器完成了这项工作,该监视器旨在监控实验室机器的工作状态;对于每个实验室机器,线程都会运行。但它实际上每10分钟才开始工作一次。

答案 6 :(得分:-1)

使用

Thread.Sleep(x); //where x >= 0

Thread.Yield();