【问题标题】:how to put my thread(user defined thread) in sleep mode in C#?如何在 C# 中将我的线程(用户定义的线程)置于睡眠模式?
【发布时间】:2013-03-08 12:45:00
【问题描述】:

我在 C# 中创建了一个线程。现在我想将我创建的线程放入某个特定的时间。然后我想开始我的线程。我的目标是,我想每天晚上 8 点调用我的 updateMark 函数。调用我的函数后,该线程将在接下来的 24 小时内休眠。所以它会在第二天晚上 8 点再次开始,并定期做同样的工作。

**My C# code:-**
    public class ThreadProcess
    {
        public static void Main()
        {

        }

        public void updateMark()
        {
             string temp=ok("hai");
        }

        public string ok(string temp)
        {
             return temp+"!!!!";
        }
    }

所以,我在另一个类的以下代码中使用线程:

        string targetTime = "08:05:00 PM";
        string currentTime = DateTime.Now.ToString("HH:mm:ss tt");

        DateTime t11 = Convert.ToDateTime(targetTime, culture);
        DateTime t21 = Convert.ToDateTime(currentTime, culture);

        ThreadProcess tp = new ThreadProcess();
        Thread myThread = new Thread(tp.updateMark);
        myThread.Start();

        if (t11.TimeOfDay.Ticks > t21.TimeOfDay.Ticks)
        {
            TimeSpan duration = DateTime.Parse(targetTime, culture).Subtract(DateTime.Parse(currentTime, culture));
            int ms = (int)duration.TotalMilliseconds;

            //Thread.Sleep(ms);i want to put my thread into sleep
        }

        while (true)
        {               
            myThread.start();

            Thread.Sleep(86400000);//put thread in sleep mode for next 24 hours...86400000 milleseconds...
        }      

请指导我摆脱这个问题...

【问题讨论】:

  • 为什么不简单地产生一个进程?
  • 为什么不让Quartz.NET 或Windows 任务计划程序解决这个问题?或者,如果您真的必须重新发明轮子,请按照 here 的建议查看 WaitHandles。

标签: c# asp.net multithreading c#-4.0


【解决方案1】:

创建一个对象并在其中存储此过程不是更合乎逻辑吗?然后在某个时间,每晚调用该对象内部的 run 方法。无需随机休眠线程,完成后内存会自行清理。

伪代码

TargetTime := 8:00PM.
// Store the target time.
Start Timer.
// Start the timer, so it will tick every second or something. That's up to you.
function tick()
{
    CurrentTime := current time.
    // Grab the current time.
    if(CurrentTime == TargetTime)
    {
         // If CurrentTime and TargetTime match, we run the code.
         // Run respective method.
    }
}

【讨论】:

  • 你能详细说明一下你的想法吗?
  • 在这种情况下,间隔非常大,我可能会采用像这样的计时器式解决方案。可以通过将初始计时器间隔设置为总间隔的一半来进行一些优化,然后在触发时重新计算剩余时间并将计时器设置为该时间的一半......依此类推,直到接近超时时间。当剩余时间少于一秒时,设置一些“在下次触发时真正运行该方法”标志并设置最后一次计时器。
  • @MartinJames:是的,你是对的。我刚刚创建了一个 C# 控制台应用程序并在 Windows 调度任务列表中配置了 exe ......它完美地完成了我的工作......谢谢马丁给我开导在这个...
【解决方案2】:

我认为你应该使用计时器而不是 Thread.Sleep

.NET 中有不同类型的计时器,您可以阅读其中的一些here

我建议基于System.Threading.Timer 进行以下简化实现:

public class ScheduledJob
{
    //Period of time the timer will be raised. 
    //Not too often to prevent the system overload.
    private readonly TimeSpan _period = TimeSpan.FromMinutes(1);
    //08:05:00 PM
    private readonly TimeSpan _targetDayTime = new TimeSpan(20, 5, 0);
    private readonly Action _action;
    private readonly Timer _timer;

    private DateTime _prevTime;

    public ScheduledJob(Action action)
    {
        _action = action;
        _timer = new Timer(TimerRaised, null, 0, _period.Milliseconds);
    }

    private void TimerRaised(object state)
    {
        var currentTime = DateTime.Now;

        if (_prevTime.TimeOfDay < _targetDayTime
            && currentTime.TimeOfDay >= _targetDayTime)
        {
            _action();
        }

        _prevTime = currentTime;
    }
}

然后,在您的客户端代码中,只需调用:

var job = new ScheduledJob(() =>
    {
        //Code to implement on timer raised. Run your thread here.
    });

【讨论】:

    猜你喜欢
    • 2011-09-28
    • 1970-01-01
    • 2011-06-01
    • 1970-01-01
    • 1970-01-01
    • 2012-12-16
    • 2018-08-09
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多