Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/.net/24.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
C# Thread.Sleep()的可接受使用_C#_Sleep - Fatal编程技术网

C# Thread.Sleep()的可接受使用

C# Thread.Sleep()的可接受使用,c#,sleep,C#,Sleep,我正在开发一个控制台应用程序,它将按设定的时间间隔(比如每30分钟)进行调度和运行。它的唯一用途是查询Web服务以更新一批数据库行 Web服务API建议每30秒调用一次,并在设置的间隔后超时。以下伪代码作为示例给出: listId := updateList(<list of terms>) LOOP WHILE NOT isUpdatingComplete(listId) END LOOP statuses := getStatuses(“LIST_ID = {listId}”

我正在开发一个控制台应用程序,它将按设定的时间间隔(比如每30分钟)进行调度和运行。它的唯一用途是查询Web服务以更新一批数据库行

Web服务API建议每30秒调用一次,并在设置的间隔后超时。以下伪代码作为示例给出:

listId := updateList(<list of terms>)
LOOP
  WHILE NOT isUpdatingComplete(listId)
END LOOP
statuses := getStatuses(“LIST_ID = {listId}”)
listId:=updateList()
环
而不是IsUpdateingComplete(listId)
端环
状态:=getStatuses(“LIST_ID={listId}”)
我用C#粗略地将其编码为:

int callCount=0;
while(callCount<5&&!client.isUpdateComplete(listId,out消息))
{
listId=client.updateList(选项、术语、输出消息);
callCount++;
睡眠(30000);
}
//获取结果状态。。。
在这种情况下使用Thread.Sleep()可以吗?我知道这通常不是一个好的做法,但从阅读原因来看,不使用它,这似乎是可以接受的用法


谢谢。

线程。睡眠
确保当前线程在至少指定的毫秒过去之前不会返回。有很多地方适合这样做,假设您的示例在后台线程上运行,那么您的示例似乎很好


有些地方你不想使用它,比如在UI线程上,或者你需要精确计时的地方。

对Sleep()的普遍反对意见是它浪费了一个线程

在您的情况下,只有1个线程(可能2个),所以这不是一个真正的问题


因此,我认为它看起来不错(但我会睡29秒来减少一些松弛)。

很好,只是一旦它进入睡眠状态,你就不能中断它,而不中止线程(这是不推荐的)


这就是为什么
ManualResetEvent
可能是一个更好的主意,因为它可以从不同的线程发出信号(“唤醒”)。

您可以继续使用thread.Sleep方法。但是,将其计划为每30分钟运行一次会更加优雅,这样您就不必关心应用程序内部的等待。

一般来说,
线程。睡眠与其他任何工具一样:完全可以使用,除非它被严重滥用。我不同意“一般不好的做法”部分,这是人们在应该做其他事情时滥用
Thread.Sleep
(即阻塞同步对象)的结果


在您的情况下,程序是单线程的,它没有UI(即线程没有消息循环),并且您不希望与外部事件同步。因此
Thread.Sleep
很好。

Thread.Sleep不是执行周期性逻辑的最佳方法。Sleep(n)表示线程将在n毫秒内放弃控制。无法保证它会在n毫秒后重新获得控制,这取决于CPU负载。

如果要将线程锁定30分钟,则应每30分钟安排一次windows任务,以便程序执行,然后结束。这样,您就不会在这么长时间内锁定线程


对于较短的时间,如30秒/1分钟,System.Thread.Sleep()非常好。超过5分钟,我将使用windows任务。(我是西班牙人,我想英文版的名字是这样的,我说的是你在控制面板上安排的任务;-)

你使用
线程。睡眠
是完全可以接受的控制台应用程序将被安排吗?如果是这样的话,为什么不每30分钟安排一次呢?更好的解决方案是使用计时器调用方法的windows服务。为什么不呢?不使用它的原因是什么?@Ray:看起来这段代码只需要2.5分钟就可以运行(5个循环,迭代之间有30秒的等待时间)。听起来这些循环计划每30分钟执行一次。换句话说,循环不会持续30分钟。@Ray我认为计划每30分钟运行一次的控制台应用程序与建议调用方每隔30秒重试一次的web服务API之间存在混淆。在本例中,它看起来像是Thread.Sleep用于分配重试时间,而不是作为调度控制台应用程序工作的机制。控制台应用程序每30分钟运行一次这一事实是一个无关的问题。我认为您的限定“假设它在后台线程上运行”是可以的,但在这种情况下,该应用程序似乎是一个控制台应用程序,将作为计划任务自动运行,所以我认为在这种情况下,没有必要确保它在后台线程上运行。如果这是一个交互式应用程序,那么我完全同意你的资格。我指的是后台线程,指在后台运行的任何线程,即不是UI线程。服务线程我会考虑后台线程。(我不是指线程对象上的
IsBackground
,它只是指如何在appexit、IIRC上销毁/清理线程)。哎呀,没看到你说的控制台。是的,这是一个有争议的术语,但它不是一个真正的背景线程,非常正确。然后我可能会说控制台应用程序不太合适……啊,我明白你的意思了。:)我本不想讨论语义,但您的评论让我意识到,在这种情况下,控制台应用程序的“主线程”可以被视为“后台”线程,因为没有用户交互。我不相信29秒的事情。。Amazon在一些API调用之间需要60秒
Thread.Sleep(60*1000)
在极少数情况下仍然会给出一个关于60秒延迟的错误,因此,在这种特定情况下,我会休眠62秒,也就是说,给它更多的延迟。YMMV和所有这些。。
int callCount = 0;
while( callCount < 5 && !client.isUpdateComplete(listId, out messages) )
{
    listId = client.updateList(options, terms, out messages);
    callCount++;
    Thread.Sleep(30000);
}
// Get resulting status...