每 n 秒唤醒一次线程

本文关键字:一次 线程 唤醒 | 更新日期: 2023-09-27 17:57:11

我正在使用C#编写WPF应用程序,我需要一些线程方面的帮助。我有三个类,每个类都需要在自己的线程中每 n 秒运行一次任务。这就是我使用 Qt4 的方式:

class myThread : public QThread
{
    void run (void)
    {
        while (true)
        {
            mMutex.lock();
            mWaitCondition.wait (&mMutex);
            // Some task
            mMutex.unlock();
        }
    }
    void wait (int timeout)
    {
        // For shutdown purposes
        if (mMutex.tryLock (timeout))
            mMutex.unlock();
    }
    void wake (void)
    {
        mWaitCondition.wakeAll();
    }
}
// Some other class has a timer which ticks
// every n seconds calling the wake function
// of the myThread class.

我从中得到的是一个受控的更新间隔。因此,如果我每秒更新 60 次,如果代码很慢并且每秒只能运行 30 次,那么这样做没有问题,但它每秒运行的时间永远不会超过 60 次。它也不会同时多次运行相同的代码。在 C# 中实现此目的的最简单方法是什么?

每 n 秒唤醒一次线程

您应该改用Timer

阅读本文

了解详细信息,或阅读本文以获取更紧凑的解释。

.NET 反应式扩展允许复杂的、基于时间的异步事件组合 - 这可能是与时间相关的行为的良好起点。

你可以使用那里的类来做到这一点

using System;
using System.Timers;
using System.Threading;
public class ClassTask
{
    System.Timers.Timer timer = null;
    public bool IsRunning { get; set; }
    public DateTime LastRunTime { get; set; }
    public bool IsLastRunSuccessful { get; set; }
    public double Interval { get; set; }
    public bool Stopped { get; set; }
    public ClassTask(double interval)
    {
        this.Interval = interval;
        this.Stopped = false;
        timer = new System.Timers.Timer(this.Interval);
        timer.Elapsed += new ElapsedEventHandler(timer_Elapsed);
        timer.Enabled = true;
    }
    public void Start()
    {
        this.Stopped = false;
        this.StartTask();
    }
    public void Stop()
    {
        this.Stopped = true;
    }
    private void StartTask()
    {
        if (!this.Stopped)
        {
            //Thread thread = new Thread(new ThreadStart(Execute));
            //thread.Start();
            Execute();
        }
    }
    private void Execute()
    {
        try
        {
            this.IsRunning = true;
            this.LastRunTime = DateTime.Now;
            // Write code here
            this.IsLastRunSuccessful = true;
        }
        catch
        {
            this.IsLastRunSuccessful = false;
        }
        finally
        {
            this.IsRunning = false;
        }
    }
    void timer_Elapsed(object sender, ElapsedEventArgs e)
    {
        if (!this.IsRunning)
            StartTask();
    }
}
using System;
using System.Data;
using System.Configuration;
public class ClassTaskScheduler
{
    ClassTask task = null;
    public ClassTaskScheduler()
    {
        this.task = new ClassTask(60000);
    }
    public void StartTask()
    {
        this.task.Start();
    }
    public void StopTask()
    {
        this.task.Stop();
    }
}

在global.asax中或你想称之为的地方

void Application_Start(object sender, EventArgs e) 
    {
        // Code that runs on application startup
        ClassTaskScheduler _scheduler = new ClassTaskScheduler();
        _scheduler.StartTask();
    }
    void Application_End(object sender, EventArgs e) 
    {
        //  Code that runs on application shutdown
        ClassTaskScheduler _scheduler = new ClassTaskScheduler();
        _scheduler.StopTask();
    }

您可以使用 Execute() 函数在给定的时间间隔内运行任务。

.NET 中的等效项是使用 ManualResetEvent 。使用带超时的 WaitOne 方法会导致等待。它还可以兼作关闭机制。这种方法的好处是很简单,一切都运行一个线程,并且相同的代码不能并行执行(因为它都在一个线程上)。

class myThread
{
  private ManualResetEvent m_WaitHandle = new ManualResetEvent(false);
  public myThread
  {
    new Thread(Run).Start();
  }
  public void Shutdown()
  {
    m_WaitHandle.Set(); // Signal the wait handle.
  }
  private void Run()
  {
    while (!m_WaitHandle.WaitOne(INTERVAL)) // The waiting happens here.
    {
      // Some task
    }
    // If execution gets here then the wait handle was signaled from the Shutdown method.
  }
}