我在互联网上找到了这本书。约瑟夫在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密集度?我刚接触多线程概念,所以我想我应该事先询问。
答案 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)
我读到您的处理器可以处理的活动有两种主要的不同类型。我可能在这些语句中有错误的措辞/语法,如果有人可以纠正语法,我将不胜感激。
计算工作(计算限制):向处理器提供纯计算任务,处理器可在其上工作,无需外部设备或组件的任何输入。
基于输入的工作(I / O界限):当您的处理器正在处理某些事情时,还需要读取或写入某些内容,或者需要等待网络活动。例如,从磁盘读取文件或下载文件。
它们之间的主要区别在于计算应该在没有等待的情况下使用,以便在尽可能最快的时间内完成任务。 例如:
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();