转:C# 定时任务实现
原文地址:http://blog.csdn.net/Netself/article/details/5766398
C#实现的定时任务类,核心代码如下:
以下代码可直接封装成 TimerTask.dll 供其它程序调用,最后是个测试类,提供了三种使用方法
//**********************************Begin TimerTask.dll ************************************//
using System;
using System.Threading;
namespace TimerTask
{
/// <summary>
/// 定时任务委托方法
/// </summary>
public delegate void TimerTaskDelegate();
/// <summary>
/// 有参数的定时任务委托方法
/// </summary>
public delegate void ParmTimerTaskDelegate(object[] parm);
/// <summary>
/// 定时任务接口类
/// </summary>
public interface ITimerTask
{
void Run();
}
/// <summary>
/// 定时任务服务类
/// 作者:Duyong
/// 编写日期:2010-07-25
///</summary>
public class TimerTaskService
{
#region 定时任务实例成员
private TimerInfo timerInfo; //定时信息
private DateTime NextRunTime; //下一次执行时间
private TimerTaskDelegate TimerTaskDelegateFun = null; //执行具体任务的委托方法
private ParmTimerTaskDelegate ParmTimerTaskDelegateFun = null; //带参数的执行具体任务的委托方法
private object[] parm = null; //参数
private ITimerTask TimerTaskInstance = null; //执行具体任务的实例
/// <summary>
/// 根据定时信息构造定时任务服务
/// </summary>
/// <param name="_timer"></param>
private TimerTaskService(TimerInfo _timer)
{
timerInfo = _timer;
}
/// <summary>
/// 根据定时信息和执行具体任务的实例构造定时任务服务
/// </summary>
/// <param name="_timer">定时信息</param>
/// <param name="_interface">执行具体任务的实例</param>
private TimerTaskService(TimerInfo _timer, ITimerTask _interface)
{
timerInfo = _timer;
TimerTaskInstance = _interface;
}
/// <summary>
/// 根据定时信息和执行具体任务的委托方法构造定时任务服务
/// </summary>
/// <param name="_timer">定时信息</param>
/// <param name="trd">执行具体任务的委托方法</param>
private TimerTaskService(TimerInfo _timer, TimerTaskDelegate trd)
{
timerInfo = _timer;
TimerTaskDelegateFun = trd;
}
/// <summary>
/// 根据定时信息和执行具体任务的委托方法构造定时任务服务
/// </summary>
/// <param name="_timer">定时信息</param>
/// <param name="ptrd">带参数执行具体任务的委托方法</param>
private TimerTaskService(TimerInfo _timer, ParmTimerTaskDelegate ptrd)
{
timerInfo = _timer;
ParmTimerTaskDelegateFun = ptrd;
}
/// <summary>
/// 设置参数
/// </summary>
/// <param name="_parm"></param>
private void setParm(object[] _parm)
{
parm = _parm;
}
/// <summary>
/// 启动定时任务
/// </summary>
public void Start()
{
//检查定时器
CheckTimer(timerInfo);
}
/// <summary>
/// 检查定时器
/// </summary>
private void CheckTimer(TimerInfo timerInfo)
{
//计算下次执行时间
getNextRunTime();
while (true)
{
DateTime DateTimeNow = DateTime.Now;
//时间比较
bool dateComp = DateTimeNow.Year == NextRunTime.Year && DateTimeNow.Month == NextRunTime.Month && DateTimeNow.Day == NextRunTime.Day;
bool timeComp = DateTimeNow.Hour == NextRunTime.Hour && DateTimeNow.Minute == NextRunTime.Minute && DateTimeNow.Second == NextRunTime.Second;
//如果当前时间等式下次运行时间,则调用线程执行方法
if (dateComp && timeComp)
{
//调用执行处理方法
if (TimerTaskDelegateFun != null)
{
TimerTaskDelegateFun();
}
else if (ParmTimerTaskDelegateFun != null)
{
ParmTimerTaskDelegateFun(parm);
}
else if (TimerTaskInstance != null)
{
TimerTaskInstance.Run();
}
else
{
Run();
}
//重新计算下次执行时间
getNextRunTime();
}
Thread.Sleep(10);
}
}
/// <summary>
/// 执行方法
/// </summary>
protected void Run()
{
//TODO.....
}
/// <summary>
/// 计算下一次执行时间
/// </summary>
/// <returns></returns>
private void getNextRunTime()
{
DateTime now = DateTime.Now;
int nowHH = now.Hour;
int nowMM = now.Minute;
int nowSS = now.Second;
int timeHH = timerInfo.Hour;
int timeMM = timerInfo.Minute;
int timeSS = timerInfo.Second;
//设置执行时间对当前时间进行比较
bool nowTimeComp = nowHH < timeHH || (nowHH <= timerInfo.Hour && nowMM < timeMM) || (nowHH <= timerInfo.Hour && nowMM <= timeMM && nowSS < timeSS);
//每天
if ("EveryDay".Equals(timerInfo.TimerType))
{
if (nowTimeComp)
{
NextRunTime = new DateTime(now.Year, now.Month, now.Day, timeHH, timeMM, timeSS);
}
else
{
NextRunTime = new DateTime(now.Year, now.Month, now.Day, timeHH, timeMM, timeSS).AddDays(1);
}
}
//每周一次
else if ("DayOfWeek".Equals(timerInfo.TimerType))
{
DayOfWeek ofweek = DateTime.Now.DayOfWeek;
int dayOfweek = Convert.ToInt32(DateTime.Now.DayOfWeek);
if (ofweek == DayOfWeek.Sunday) dayOfweek = 7;
if (dayOfweek < timerInfo.DateValue)
{
int addDays = timerInfo.DateValue - dayOfweek;
NextRunTime = new DateTime(now.Year, now.Month, now.Day, timeHH, timeMM, timeSS).AddDays(addDays);
}
else if (dayOfweek == timerInfo.DateValue && nowTimeComp)
{
NextRunTime = new DateTime(now.Year, now.Month, now.Day, timeHH, timeMM, timeSS);
}
else
{
int addDays = 7 - (dayOfweek - timerInfo.DateValue);
NextRunTime = new DateTime(now.Year, now.Month, now.Day, timeHH, timeMM, timeSS).AddDays(addDays);
}
}
//每月一次
else if ("DayOfMonth".Equals(timerInfo.TimerType))
{
if (now.Day < timerInfo.DateValue)
{
NextRunTime = new DateTime(now.Year, now.Month, timerInfo.DateValue, timeHH, timeMM, timeSS);
}
else if (now.Day == timerInfo.DateValue && nowTimeComp)
{
NextRunTime = new DateTime(now.Year, now.Month, now.Day, timeHH, timeMM, timeSS);
}
else
{
NextRunTime = new DateTime(now.Year, now.Month, timerInfo.DateValue, timeHH, timeMM, timeSS).AddMonths(1);
}
}
//指定日期
else if ("DesDate".Equals(timerInfo.TimerType))
{
NextRunTime = new DateTime(timerInfo.Year, timerInfo.Month, timerInfo.Day, timeHH, timeMM, timeSS);
}
//循环指定天数
else if ("LoopDays".Equals(timerInfo.TimerType))
{
NextRunTime = new DateTime(now.Year, now.Month, now.Day, timeHH, timeMM, timeSS).AddDays(timerInfo.DateValue);
}
}
#endregion
#region 创建定时任务静态方法
/// <summary>
/// 使用委托方法创建定时任务
/// <param name="info"></param>
/// <param name="_trd"></param>
/// <returns></returns>
public static Thread CreateTimerTaskService(TimerInfo info, TimerTaskDelegate _trd)
{
TimerTaskService tus = new TimerTaskService(info, _trd);
//创建启动线程
Thread ThreadTimerTaskService = new Thread(new ThreadStart(tus.Start));
return ThreadTimerTaskService;
}
/// <summary>
/// 使用带参数的委托方法创建定时任务
/// </summary>
/// <param name="info"></param>
/// <param name="_ptrd"></param>
/// <param name="parm"></param>
/// <returns></returns>
public static Thread CreateTimerTaskService(TimerInfo info, ParmTimerTaskDelegate _ptrd, object[] parm)
{
TimerTaskService tus = new TimerTaskService(info, _ptrd);
tus.setParm(parm);
//创建启动线程
Thread ThreadTimerTaskService = new Thread(new ThreadStart(tus.Start));
return ThreadTimerTaskService;
}
/// <summary>
/// 使用实现定时接口ITimerTask的实例创建定时任务
/// </summary>
/// <param name="info"></param>
/// <param name="_ins"></param>
/// <returns></returns>
public static Thread CreateTimerTaskService(TimerInfo info, ITimerTask _ins)
{
TimerTaskService tus = new TimerTaskService(info, _ins);
//创建启动线程
Thread ThreadTimerTaskService = new Thread(new ThreadStart(tus.Start));
return ThreadTimerTaskService;
}
#endregion
}
/// <summary>
/// 定时信息类
/// TimerType 类型:EveryDay(每天),DayOfWeek(每周),DayOfMonth(每月),DesDate(指定日期),LoopDays(循环天数)
/// DateValue 日期值:TimerType="DayOfWeek"时,值为1-7表示周一到周日;TimerType="DayOfMonth"时,值为1-31表示1号到31号,
/// TimerType="LoopDays"时,值为要循环的天数,TimerType为其它值时,此值无效
/// Year 年:TimerType="DesDate"时,此值有效
/// Month 月:TimerType="DesDate"时,此值有效
/// Day 日:TimerType="DesDate"时,此值有效
/// Hour 时:]
/// Minute 分: > 设置的执行时间
/// Second 秒:]
/// </summary>
public class TimerInfo
{
public string TimerType;
public int DateValue;
public int Year;
public int Month;
public int Day;
public int Hour = 00;
public int Minute = 00;
public int Second = 00;
}
}
//**********************************End TimerTask.dll ****************************************//
以下是测试类,提供了三种使用方法
using System;
using System.Threading;
using TimerTask;
namespace Test
{
/// <summary>
/// 定时任务测试类
/// 提供三种调用方法
/// TimerInfo持久化代码省略,此信息可保存到数据库或配置文件
/// </summary>
public class TestTimerTask:ITimerTask
{
/// <summary>
/// 程序入口
/// </summary>
[STAThread]
public static void Main()
{
///程序调用举例
///
//每天12点执行
TimerTask.TimerInfo timerInfo = new TimerTask.TimerInfo();
timerInfo.TimerType = "EveryDay";
timerInfo.Hour = 12;
timerInfo.Minute =00;
timerInfo.Second = 00;
////每周日12点执行
//TimerUpdate.TimerInfo timerInfo = new TimerUpdate.TimerInfo();
//timerInfo.TimerType = "DayOfWeek";
//timerInfo.DateValue = 7;
//timerInfo.Hour = 12;
//timerInfo.Minute = 00;
//timerInfo.Second = 00;
////每月1号12点执行
//TimerUpdate.TimerInfo timerInfo = new TimerUpdate.TimerInfo();
//timerInfo.TimerType = "DayOfMonth";
//timerInfo.DateValue = 1;
//timerInfo.Hour = 12;
//timerInfo.Minute = 00;
//timerInfo.Second = 00;
////指定某一天12点执行
//TimerUpdate.TimerInfo timerInfo = new TimerUpdate.TimerInfo();
//timerInfo.TimerType = "DesDate";
//timerInfo.Year = 2010;
//timerInfo.Month = 12;
//timerInfo.Day = 01;
//timerInfo.Hour = 12;
//timerInfo.Minute = 00;
//timerInfo.Second = 00;
////5天后12点执行
//TimerUpdate.TimerInfo timerInfo = new TimerUpdate.TimerInfo();
//timerInfo.TimerType = "LoopDays";
//timerInfo.DateValue = 5;
//timerInfo.Hour = 12;
//timerInfo.Minute = 00;
//timerInfo.Second = 00;
//第一种调用方法
TestTimerTask test1 = new TestTimerTask();
TimerTaskDelegate trd = new TimerTaskDelegate(test1.TestTimerTask1);
//创建定时任务线程
Thread ThreadTimerTaskService1 = TimerTaskService.CreateTimerTaskService(timerInfo, trd);
ThreadTimerTaskService1.Start();
//第二种调用方法
TestTimerTask test2 = new TestTimerTask();
ParmTimerTaskDelegate ptrd = new ParmTimerTaskDelegate(test2.TestTimerTask2);
object[] p = new object[] { "参数1", "参数2" };
//创建定时任务线程
Thread ThreadTimerTaskService2 = TimerTaskService.CreateTimerTaskService(timerInfo, ptrd, p);
ThreadTimerTaskService2.Start();
//第三种调用方法
TestTimerTask test3 = new TestTimerTask(); //TestTimerTask已实现ITimerTask接口
//创建定时任务线程
Thread ThreadTimerTaskService3 = TimerTaskService.CreateTimerTaskService(timerInfo, test3);
ThreadTimerTaskService3.Start();
}
public void TestTimerTask1()
{
Console.WriteLine("不带参数的定时任务已执行!");
Console.ReadLine();
}
public void TestTimerTask2(object[] parm)
{
Console.WriteLine("带object[]参数的定时任务已执行!");
if (parm != null && parm.Length > 0)
{
foreach (object o in parm)
{
Console.WriteLine("参数内容:" + o.ToString());
}
}
Console.ReadLine();
}
/// <summary>
/// 实现ITimerTask接口中的Run方法
/// </summary>
public void Run()
{
Console.WriteLine("ITimerTask接口实现的定时任务已执行!");
Console.ReadLine();
}
}
}
转:C# 定时任务实现的更多相关文章
- Java定时任务的常用实现
Java的定时任务有以下几种常用的实现方式: 1)Timer 2)ScheduledThreadPoolExecutor 3)Spring中集成Cron Quartz 接下来依次介绍这几类具体实现的方 ...
- [转]Java实现定时任务的三种方法
在应用里经常都有用到在后台跑定时任务的需求.举个例子,比如需要在服务后台跑一个定时任务来进行非实时计算,清除临时数据.文件等.在本文里,我会给大家介绍3种不同的实现方法: 普通thread实现 Tim ...
- 使用python crontab设置linux定时任务
熟悉linux的朋友应该知道在linux中可以使用crontab设置定时任务.可以通过命令crontab -e编写任务.当然也可以直接写配置文件设置任务. 但是有时候希望通过脚本自动设置,比如我们应用 ...
- C#定时任务组件之FluentScheduler
FluentScheduler是.NET开源处理定时任务组件 1.任务的创建注册 public static void TaskActionByMinutes(Action action, int c ...
- 浅谈 linux 例行性工作 crontab (linux定时任务)
定时任务大家都挺说过,就好比你手机上的闹钟,到了指定的时候就会响起. 今天在对redis缓存进行定时储存时又操作了一把,发现一些细节,写的不好.大家就将就看吧, 首先 简单介绍一下linux 例行性工 ...
- SpringMVC中定时任务配置
在项目中使用定时任务是常有的事,比如每天定时进行数据同步或者备份等等. 以前在从事C语言开发的时候,定时任务都是通过写个shell脚本,然后添加到linux定时任务中进行调度的. 现在使用Spring ...
- springboot(九):定时任务
在我们的项目开发过程中,经常需要定时任务来帮助我们来做一些内容,springboot默认已经帮我们实行了,只需要添加相应的注解就可以实现 1.pom包配置 pom包里面只需要引入springboot ...
- 详解java定时任务
在我们编程过程中如果需要执行一些简单的定时任务,无须做复杂的控制,我们可以考虑使用JDK中的Timer定时任务来实现.下面LZ就其原理.实例以及Timer缺陷三个方面来解析JavaTimer定时器. ...
- [JAVA]定时任务之-Quartz使用篇
Quartz是OpenSymphony开源组织在Job scheduling领域又一个开源项目,它可以与J2EE与J2SE应用程序相结合也可以单独使用.Quartz可以用来创建简单或为运行十个,百个, ...
- 【译】Spring 4 基于TaskScheduler实现定时任务(注解)
前言 译文链接:http://websystique.com/spring/spring-job-scheduling-with-scheduled-enablescheduling-annotati ...
随机推荐
- C++链接器工具错误:LNK2001, LNK2019(转载)
这是归属于链接器工具错误 这一类. 无法解析的外部符号“symbol” 代码引用了链接器无法在库和对象文件中找到的内容(如函数.变量或标签). 可能的原因 代码请求的内容不存在(例如,符号拼写错误或使 ...
- Interfaces
阅读Java的官方Doc,总结如下. What is Interface An interface is a reference type, similar to a class, that can ...
- 法爱格2014 春夏新款欧美纯色修身高腰无袖吊带V领 拼接性感 连衣裙 黑色 M【图片 价格 品牌 报价】-京东
法爱格2014 春夏新款欧美纯色修身高腰无袖吊带V领 拼接性感 连衣裙 黑色 M[图片 价格 品牌 报价]-京东 法爱格2014 春夏新款欧美纯色修身高腰无袖吊带V领 拼接性感 连衣裙 黑色 M
- Windows系统结构
四种用户模式进程:1.系统支持进程,比如登录进程和会话管理器,并不是Windows服务,不有服务控制管理器启动2.服务进程,一些以Windows服务方式来运行的组件3.用户应用进程4.环境子系统服务器 ...
- Html5 Canvas 实现滚动的图片
今天一直在找html5 canvas的使用实例.想画一张地图,再画个小车在上面跑.运气好找到了一个大神写的js代码.该代码实现了图片的左右来回滚动,现在粘贴在博客里记录一下: <html> ...
- [RxJS] Toggle A Stream On And Off With RxJS
This lesson covers how to toggle an observable on and off from another observable by showing how to ...
- hdu 3917 最大重量封闭图
/*最大重量封闭图: 意甲冠军:一些城市要建路需要负责一些公司,每家公司都需要缴纳个税.该公司将需要花费每路,另一个限制条件,如果那家公司a既定a-b.公司b既定b-c然后选择 公司a 你必须选择一个 ...
- Android UI开发详解之ActionBar .
在Android3.0之后,Google对UI导航设计上进行了一系列的改革,其中有一个非常好用的新功能就是引入的ActionBar,他用于取代3.0之前的标题栏,并提供更为丰富的导航效果. 一.添加A ...
- android设备之间屏幕共享
近期公司在开发一款android的设备把屏幕投射到手机上.同一时候手机还能够触控.键盘操作.这样.就达到了屏幕共享的目的. 思考了一下.主要思路: 1.将截图所获取的位图用ffmpeg编码成视频流. ...
- 关于SetCapture() 和 ReleaseCapture()的使用方法
查MSND,对SetCapture()函数的说明为:“该函数在属于当前线程的指定窗体里设置鼠标捕获.一旦窗体捕获了鼠标,全部鼠标输入都针对该窗体,不管光标是否在窗体的边界内.同一时刻仅仅能有一个窗体捕 ...