public class ThreadHelper
{
private static RunIntervalTimeout TimeoutInterval = new RunIntervalTimeout();
#region Timeout
/// <summary>
/// 多少毫秒后执行任务,适用于执行时间短,不需要单独开线程的程序
/// </summary>
/// <param name="vFrom">需要执行的窗体</param>
/// <param name="vExecute">需要执行的程序</param>
/// <param name="vTime">间隔时间</param>
/// <returns>执行标志</returns>
public static string SetTimeout(Form vForm, ThreadDelegateCode vExecute)
{
return TimeoutInterval.Add(vForm, vExecute, 0, false);
}
/// <summary>
/// 多少毫秒后执行任务,适用于执行时间短,不需要单独开线程的程序
/// </summary>
/// <param name="vFrom">需要执行的窗体</param>
/// <param name="vExecute">需要执行的程序</param>
/// <param name="vTime">间隔时间</param>
/// <returns>执行标志</returns>
public static string SetTimeout(Form vForm, ThreadDelegateCode vExecute, int vTime)
{
return TimeoutInterval.Add(vForm, vExecute, vTime, false);
}
/// <summary>
/// 多少毫秒后执行任务,适用于执行时间短,不需要单独开线程的程序
/// </summary>
/// <param name="vExecute">需要执行的程序</param>
/// <returns>执行标志</returns>
public static string SetTimeout(ThreadDelegateCode vExecute)
{
return TimeoutInterval.Add(vExecute, 0, false);
}
/// <summary>
/// 多少毫秒后执行任务,适用于执行时间短,不需要单独开线程的程序
/// </summary>
/// <param name="vExecute">需要执行的程序</param>
/// <param name="vTime">间隔时间</param>
/// <returns>执行标志</returns>
public static string SetTimeout(ThreadDelegateCode vExecute, int vTime)
{
return TimeoutInterval.Add(vExecute, vTime, false);
}
/// <summary>
/// 清除需要执行的任务
/// </summary>
/// <param name="flag">执行标志</param>
public static bool ClearTimeout(string flag)
{
return TimeoutInterval.Remove(flag);
}
/// <summary>
/// 清除需要执行的任务
/// </summary>
/// <param name="vExecute">执行的方法,注意有多个同样的方法时,只会清除第一个</param>
public static bool ClearTimeout(ThreadDelegateCode vExecute)
{
return TimeoutInterval.Remove(vExecute);
}
#endregion
#region Interval
/// <summary>
/// 每隔多少毫秒执行任务,适用于执行时间短,不需要单独开线程的程序
/// </summary>
/// <param name="vFrom">需要执行的窗体</param>
/// <param name="vExecute">需要执行的程序</param>
/// <param name="vTime">间隔时间</param>
/// <returns>执行标志</returns>
public static string SetInterval(Form vForm, ThreadDelegateCode vExecute, int vTime)
{
return TimeoutInterval.Add(vForm, vExecute, vTime, true);
}
/// <summary>
/// 每隔多少毫秒执行任务,适用于执行时间短,不需要单独开线程的程序
/// </summary>
/// <param name="vExecute">需要执行的程序</param>
/// <param name="vTime">间隔时间</param>
/// <returns>执行标志</returns>
public static string SetInterval(ThreadDelegateCode vExecute, int vTime)
{
return TimeoutInterval.Add(vExecute, vTime, true);
}
/// <summary>
/// 清除需要执行的任务
/// </summary>
/// <param name="flag">执行标志</param>
public static bool ClearInterval(string flag)
{
return TimeoutInterval.Remove(flag);
}
/// <summary>
/// 清除需要执行的任务
/// </summary>
/// <param name="vExecute">执行的方法,注意有多个同样的方法时,只会清除第一个</param>
public static bool ClearInterval(ThreadDelegateCode vExecute)
{
return TimeoutInterval.Remove(vExecute);
}
#endregion
public static void Sleep(int p)
{
Thread.Sleep(p);
}
public static Thread RunThread(ThreadDelegateCode vExecute)
{
ThreadStart start = new ThreadStart(delegate()
{
try
{
vExecute();
}
catch (Exception ex)
{
LogHelper.WriteLog(ex);
}
});
Thread thread = new Thread(start);
thread.IsBackground = true;
thread.Start();
return thread;
}
public static Thread RunThread(RunInterval vInterval)
{
Thread vThread = RunThread(delegate()
{
while (!vInterval.Break)
{
try
{
vInterval.Code();
}
catch (Exception ex)
{
LogHelper.WriteLog(ex);
}
Thread.Sleep(vInterval.Time);
}
});
vInterval.Thread = vThread;
return vThread;
}
}
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Windows.Forms;
using System.Threading;
namespace Piaost
{
public class RunIntervalTimeout
{
private class ExecuteData
{
public ExecuteData()
{
this.Date = DateTime.Now;
this.ExecuteCount = 0;
this.ExecuteError = 0;
this.IsExecute = false;
this.Execute = null;
this.Flag = StringHelper.GetGUID();
this.Time = 0;
this.Execute = null;
this.IsRepeat = false;
}
public DateTime Date; //上次执行时间、当前执行时间
public double ExecuteCount; //执行次数
public double ExecuteError; //执行错误次数
public bool IsExecute; //是否正在执行
public Exception Exception; //最后异常对象
public string Flag; //执行标识
public int Time; //间隔时间、延迟时间
public ThreadDelegateCode Execute; //执行的代码
public bool IsRepeat; //是否重复执行
}
private RunCode Main = new RunCode(); //监控Timeout、Interval的执行
//private AutoResetEvent m_Event = new AutoResetEvent(false);
private object m_Lock = new object(); //锁
private Queue<RunCode> WaitThreadList = new Queue<RunCode>(); //空闲线程对象
private List<RunCode> TotalThreadList = new List<RunCode>(); //所有的线程对象
private List<ExecuteData> DataList = new List<ExecuteData>(); //正在执行的队列
public RunIntervalTimeout()
{
this.Main.KeepAlive = true;
this.Main.KeepAliveSleep = 10;
this.Main.AddCode(this.Execute);
}
private void Execute()
{
do
{
//m_Event.WaitOne();
ExecuteData vWait = this.GetWait();
if (vWait == null)
{
break;
}
RunCode vRun = this.GetWaitThread();
this.ExecuteItem(vRun, vWait);
} while (true);
}
private void ExecuteItem(RunCode vRun, ExecuteData vExecute)
{
if (vExecute == null)
{
AddRun(vRun);
}
vExecute.Date = DateTime.Now;
vExecute.ExecuteCount++;
vExecute.IsExecute = true;
vRun.ClearCode();
vRun.AddCode(delegate()
{
try
{
vExecute.Execute();
}
catch (Exception ex)
{
vExecute.ExecuteError++;
vExecute.Exception = ex;
throw ex;
}
finally
{
vExecute.IsExecute = false;
vExecute.Date = DateTime.Now;
AddRun(vRun);
if (!vExecute.IsRepeat)
{
this.Remove(vExecute.Flag); //只执行一次则从队列中移除
}
}
});
}
private ExecuteData GetWait()
{
ExecuteData vData = null;
lock (this.m_Lock)
{
// 未到执行时间,则移动到队列的最后面
DateTime vNow = DateTime.Now;
foreach (ExecuteData vWait in this.DataList)
{
if (vWait.Date > vNow)
{
vWait.Date = vNow;
}
if (vWait.IsExecute || (vNow - vWait.Date).TotalMilliseconds < vWait.Time)
{
continue;
}
vData = vWait;
break;
}
}
return vData;
}
private void InitTimer()
{
int vMinTime = 100;
foreach (ExecuteData vWait in this.DataList)
{
if (vWait.Time < vMinTime)
{
vMinTime = vWait.Time;
}
}
this.Main.KeepAliveSleep = vMinTime;
}
private void AddRun(RunCode vRun)
{
lock (this.m_Lock)
{
WaitThreadList.Enqueue(vRun);
}
}
private RunCode GetWaitThread()
{
RunCode vThread = null;
lock (this.m_Lock)
{
if (WaitThreadList.Count > 0)
{
vThread = WaitThreadList.Dequeue();
}
else
{
vThread = new RunCode();
vThread.KeepAlive = false;
TotalThreadList.Add(vThread);
}
}
return vThread;
}
public string Add(ThreadDelegateCode vCode, int vTime, bool isRepeat)
{
ExecuteData vData = new ExecuteData()
{
Execute = vCode,
Time = vTime,
IsRepeat = isRepeat
};
lock (this.m_Lock)
{
this.DataList.Add(vData);
this.InitTimer();
//this.m_Event.Set();
}
return vData.Flag;
}
public string Add(Form vForm, ThreadDelegateCode vExecute, int vTime, bool isRepeat)
{
string flag = Add(vExecute, vTime, isRepeat);
#if CE
vForm.Closed += delegate(object sender, EventArgs e)
#else
vForm.FormClosing += delegate(object sender, FormClosingEventArgs e)
#endif
{
Remove(flag);
};
return flag;
}
public bool Remove(ThreadDelegateCode vCode)
{
ExecuteData vData = null;
lock (m_Lock)
{
foreach (ExecuteData vItem in DataList)
{
if (vItem != null && vItem.Execute == vCode)
{
vData = vItem;
break;
}
}
}
return this.Remove(vData);
}
public bool Remove(string vGUID)
{
ExecuteData vData = null;
lock (m_Lock)
{
foreach (ExecuteData vItem in DataList)
{
if (vItem != null && vItem.Flag == vGUID)
{
vData = vItem;
break;
}
}
}
return this.Remove(vData);
}
private bool Remove(ExecuteData vData)
{
if (vData == null)
{
return false;
}
lock (m_Lock)
{
bool ret = this.DataList.Remove(vData);
this.InitTimer();
if (this.DataList.Count == 0)
{
//this.m_Event.Reset();
}
return ret;
}
}
}
}