C#定点任务代码 类似Windows计划任务(健壮性高)

清泛原创
C#只提供Timer定时器(C++ SetTimer 类似),通过设置一个时间间隔来定时触发执行任务。那么定点执行任务怎么实现呢?
原理:每次通过计算得出下次定点任务与现在时点的事件间隔,作为Timer的时间间隔,从而实现任务的定点执行。原理比较简单,代码中都有注释,有类似需求的童鞋可以直接用作项目中,免测试哦~~~
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Diagnostics;
using System.Linq;
using System.ServiceProcess;
using System.Text;
using System.Timers;

namespace PlanDemoService
{
    public partial class Service1 : ServiceBase
    {
        public Service1()
        {
            InitializeComponent();
        }

        // 每天执行一次的时间点(最好写在配置中,这里为了方便展示)
        private string onceDoStr = "18:00";
        private DateTime onceDoTime;

        // 定时执行一次        
        private Timer onceDoTimer = new Timer();

        /// <summary>
        /// 定时器触发事件
        /// </summary>
        /// <param name="sender"></param>
        /// <param name="e"></param>
        private void OnceDoTimer_Elapsed(object sender, ElapsedEventArgs e)
        {
            UpdateOnceDoTimePeriod();

            // 更新下次执行间隔
            SetNextOnceDoInterval();

            if (DateTime.Now.ToString("HH:mm").CompareTo(onceDoStr.Trim()) >= 0)
            {
                // 可能由于系统原因导致触发过早的,不执行
                onceDoMain();
            }
        }

        /// <summary>
        /// 设置定时器间隔时间
        /// </summary>
        private void SetNextOnceDoInterval()
        {
            TimeSpan spanNextDay = new TimeSpan(1, 0, 0, 0);

            if (DateTime.Now < onceDoTime)
            {
                onceDoTimer.Interval = (onceDoTime - DateTime.Now).TotalMilliseconds;
                Loger.Log(string.Format("定时任务将于{0}执行一次。", onceDoTime.ToString("yyyy-MM-dd HH:mm:ss")), "PlanDemoService");
            }

            if (DateTime.Now > onceDoTime)
            {
                onceDoTimer.Interval = (onceDoTime + spanNextDay - DateTime.Now).TotalMilliseconds;
                Loger.Log(string.Format("下次定时任务将于{0}执行一次。", (onceDoTime + spanNextDay).ToString("yyyy-MM-dd HH:mm:ss")), "PlanDemoService");
            }
        }

        /// <summary>
        /// 更新任务触发时间(按每天最新日期)
        /// </summary>
        private void UpdateOnceDoTimePeriod()
        {
            string[] parts = onceDoStr.Split(':');
            onceDoTime = new DateTime(DateTime.Now.Year, DateTime.Now.Month, DateTime.Now.Day,
                int.Parse(parts[0]), int.Parse(parts[1]), 0);
        }

        /// <summary>
        /// 任务执行
        /// </summary>
        private void onceDoMain()
        {
            Loger.Log("任务执行!", "PlanDemoService");
        }

        protected override void OnStart(string[] args)
        {
            try
            {
                UpdateOnceDoTimePeriod();
            }
            catch (Exception e)
            {
                Loger.Log("时间配置有误!" + e.Message, "PlanDemoService");
                throw e;
            }

            onceDoTimer.Elapsed += new ElapsedEventHandler(OnceDoTimer_Elapsed);
            SetNextOnceDoInterval();
            onceDoTimer.Start();
        }

        protected override void OnStop()
        {
            onceDoTimer.Stop();
            Loger.Log("服务已停止!", "PlanDemoService");
        }
    }
}
完整的工程代码下载:PlanDemoService.zip



最后附上C#添加Windows系统服务的过程:

C# 定点任务 计划任务

分享到:
评论加载中,请稍后...
创APP如搭积木 - 创意无限,梦想即时!
回到顶部