控制台应用程序占用大量 CPU 资源
Console Application takes of a lot of CPU ressource
我有一个非常简单的控制台应用程序,它会查看文件夹并在几秒钟后删除所有文件。
代码
private static void Main(string[] args)
{
ILogger logger = new LoggerWriter(ConfigurationManager.AppSettings["Log"]);
Task.Factory.StartNew(() =>
{
while (true)
{
var time = int.Parse(ConfigurationManager.AppSettings["Interval"]);
Thread.Sleep(time);
var directory = new DirectoryInfo(ConfigurationManager.AppSettings["Path"]);
foreach (var file in directory.GetFiles())
{
file.Delete();
var log = new Logger {DateTime = DateTime.Now, Action = $"File {file.FullName} will be deleted."};
logger.Write(log);
}
}
}, TaskCreationOptions.LongRunning).ContinueWith(t =>
{
if (t.Exception != null)
Console.WriteLine(t.Exception.Message);
});
Console.WriteLine("Press Ctrl+C to stop.");
while (
!(Console.KeyAvailable && (Console.ReadKey(true).Key == ConsoleKey.C) &&
(Console.ReadKey(true).Modifiers == ConsoleModifiers.Control)))
{
// do something
}
}
}
当我 运行 windows 服务器 2008 上的应用程序与 .NET 4 任务管理器显示如下:
当我使用FileWatcher时,也是同样的场景。怎么了?
您的第二个 while 循环是一个死循环,因此 CPU 使用率很高。事实上,Ctrl+C 是控制台应用程序的默认中断键,您不需要编写代码来"implement"此功能。
顺便说一句,从你的代码来看,我认为你想在给定的时间间隔内删除特定目录中的文件。看看FileSystemWatcher
,watching目录修改时会通知
这绝对是您处理 Control-C 的方式:
while (
!(Console.KeyAvailable && (Console.ReadKey(true).Key == ConsoleKey.C) &&
(Console.ReadKey(true).Modifiers == ConsoleModifiers.Control)))
{
// do something
}
这个循环会给你 50% cpu 的时间。
像这样的东西可以解决这个问题:
Console.CancelKeyPress += delegate {
// call methods to clean up
};
应用于您的代码:
Console.WriteLine("Press Ctrl+C to stop.");
var exitEvent = new ManualResetEvent(false);
Console.CancelKeyPress += (sender, eventArgs) => {
eventArgs.Cancel = true;
exitEvent.Set();
};
exitEvent.WaitOne();
要使其完成,您必须取消在 CancelKeyPress 事件处理程序中正确启动的任务
我有一个非常简单的控制台应用程序,它会查看文件夹并在几秒钟后删除所有文件。
代码
private static void Main(string[] args)
{
ILogger logger = new LoggerWriter(ConfigurationManager.AppSettings["Log"]);
Task.Factory.StartNew(() =>
{
while (true)
{
var time = int.Parse(ConfigurationManager.AppSettings["Interval"]);
Thread.Sleep(time);
var directory = new DirectoryInfo(ConfigurationManager.AppSettings["Path"]);
foreach (var file in directory.GetFiles())
{
file.Delete();
var log = new Logger {DateTime = DateTime.Now, Action = $"File {file.FullName} will be deleted."};
logger.Write(log);
}
}
}, TaskCreationOptions.LongRunning).ContinueWith(t =>
{
if (t.Exception != null)
Console.WriteLine(t.Exception.Message);
});
Console.WriteLine("Press Ctrl+C to stop.");
while (
!(Console.KeyAvailable && (Console.ReadKey(true).Key == ConsoleKey.C) &&
(Console.ReadKey(true).Modifiers == ConsoleModifiers.Control)))
{
// do something
}
}
}
当我 运行 windows 服务器 2008 上的应用程序与 .NET 4 任务管理器显示如下:
当我使用FileWatcher时,也是同样的场景。怎么了?
您的第二个 while 循环是一个死循环,因此 CPU 使用率很高。事实上,Ctrl+C 是控制台应用程序的默认中断键,您不需要编写代码来"implement"此功能。
顺便说一句,从你的代码来看,我认为你想在给定的时间间隔内删除特定目录中的文件。看看FileSystemWatcher
,watching目录修改时会通知
这绝对是您处理 Control-C 的方式:
while (
!(Console.KeyAvailable && (Console.ReadKey(true).Key == ConsoleKey.C) &&
(Console.ReadKey(true).Modifiers == ConsoleModifiers.Control)))
{
// do something
}
这个循环会给你 50% cpu 的时间。
像这样的东西可以解决这个问题:
Console.CancelKeyPress += delegate {
// call methods to clean up
};
应用于您的代码:
Console.WriteLine("Press Ctrl+C to stop.");
var exitEvent = new ManualResetEvent(false);
Console.CancelKeyPress += (sender, eventArgs) => {
eventArgs.Cancel = true;
exitEvent.Set();
};
exitEvent.WaitOne();
要使其完成,您必须取消在 CancelKeyPress 事件处理程序中正确启动的任务