标签:
it |
分类: 软件 |
提问者: mokeymokey - 试用期 一级
您好,
程序语言中使用的Timer是做不到准确定时的,这与使用的编程语言没有关系,而是因为受系统时钟的影响,Timer事件产生的最小值不是1毫秒,而是55毫秒,这点在VB、C++和C#中都是相同的,您可以使用在Timer_Tick事件中获取系统当前时间并计算TimeSpan来获取经过的时间。
有关Timer控件Interval属性的限制问题,您可以参考MSDN:
http://msdn.microsoft.com/library/chs/default.asp?url=/library/CHS/vbcon/html/vbconlimitationsoftimercontrolsintervalproperty.asp
希望这些信息对您有帮助。
程序语言中使用的Timer是做不到准确定时的,这与使用的编程语言没有关系,而是因为受系统时钟的影响,Timer事件产生的最小值不是1毫秒,而是55毫秒,这点在VB、C++和C#中都是相同的,您可以使用在Timer_Tick事件中获取系统当前时间并计算TimeSpan来获取经过的时间。
有关Timer控件Interval属性的限制问题,您可以参考MSDN:
http://msdn.microsoft.com/library/chs/default.asp?url=/library/CHS/vbcon/html/vbconlimitationsoftimerc
希望这些信息对您有帮助。
回答者:david_zha0 - 高级魔法师 六级 9-7 17:27
评价已经被关闭 目前有 0 个人评价
不好 50% (0) |
.NET Framework提供三种Timer
Server Timers System.Timers.Timer
Thread Timers System.Threading.Timer
Windows Timers System.Windows.Forms.Timer
其中Windows Timers只是提供了和以前的WinAPI 一样的Timer,仍然是基于消息,仍然是单线程, 会有不准时的现象
其它两个就不同了,他们是基于线程池的Thread Pool,这样最大的好处在于,产生的时间间隔准确均匀。
Server Timers 和 Thread Timers 的不同在于ServerTimers 是基于事件的,Thread Timers是基于回调函数
我更喜欢Thread Timer,比较轻量级方便易用。
但是这样的Timer也有问题,就是由于时多线程定时器,就会出现如果一个Timer处理没有完成,到了时间下一个
照样会发生,这就会导致重入问题
对付重入问题通常的办法是加锁,但是对于 Timer却不能简单的这样做,你需要评估一下
首先Timer处理里本来就不应该做太需要时间的事情,或者花费时间无法估计的事情,比同远方的服务器建立一个网络连接,这样的做法尽量避免
如果实在无法避免,那么要评估Timer处理超时是否经常发生,如果是很少出现,那么可以用lock(Object)的方法来防止重入
如果这种情况经常出现呢?那就要用另外的方法来防止重入了
我们可以设置一个标志,表示一个Timer处理正在执行,下一个Timer发生的时候发现上一个没有执行完就放弃执行
static int inTimer = 0;
public static void threadTimerCallback(Object obj)
{
if ( inTiemr == 0 )
{
inTimer = 1;
Console.WriteLine("Time:{0}, \tThread ID:{1}", DateTime.Now, Thread.CurrentThread.GetHashCode());
Thread.Sleep(2000);
inTimer = 0;
}
}
但是在多线程下给inTimer赋值不够安全,还好Interlocked.Exchange提供了一种轻量级的线程安全的给对象赋值的方法
static int inTimer = 0;
public static void threadTimerCallback(Object obj)
{
if ( Interlocked.Exchange(ref inTimer, 1) == 0 )
{
Console.WriteLine("Time:{0}, \tThread ID:{1}", DateTime.Now, Thread.CurrentThread.GetHashCode());
Thread.Sleep(250);
Interlocked.Exchange(ref inTimer, 0);
Server Timers System.Timers.Timer
Thread Timers System.Threading.Timer
Windows Timers System.Windows.Forms.Timer
其中Windows Timers只是提供了和以前的WinAPI 一样的Timer,仍然是基于消息,仍然是单线程, 会有不准时的现象
其它两个就不同了,他们是基于线程池的Thread Pool,这样最大的好处在于,产生的时间间隔准确均匀。
Server Timers 和 Thread Timers 的不同在于ServerTimers 是基于事件的,Thread Timers是基于回调函数
我更喜欢Thread Timer,比较轻量级方便易用。
但是这样的Timer也有问题,就是由于时多线程定时器,就会出现如果一个Timer处理没有完成,到了时间下一个
照样会发生,这就会导致重入问题
对付重入问题通常的办法是加锁,但是对于 Timer却不能简单的这样做,你需要评估一下
首先Timer处理里本来就不应该做太需要时间的事情,或者花费时间无法估计的事情,比同远方的服务器建立一个网络连接,这样的做法尽量避免
如果实在无法避免,那么要评估Timer处理超时是否经常发生,如果是很少出现,那么可以用lock(Object)的方法来防止重入
如果这种情况经常出现呢?那就要用另外的方法来防止重入了
我们可以设置一个标志,表示一个Timer处理正在执行,下一个Timer发生的时候发现上一个没有执行完就放弃执行
static int inTimer = 0;
public static void threadTimerCallback(Object obj)
{
if ( inTiemr == 0 )
{
inTimer = 1;
Console.WriteLine("Time:{0}, \tThread ID:{1}", DateTime.Now, Thread.CurrentThread.GetHashCode());
Thread.Sleep(2000);
inTimer = 0;
}
}
但是在多线程下给inTimer赋值不够安全,还好Interlocked.Exchange提供了一种轻量级的线程安全的给对象赋值的方法
static int inTimer = 0;
public static void threadTimerCallback(Object obj)
{
if ( Interlocked.Exchange(ref inTimer, 1) == 0 )
{
Console.WriteLine("Time:{0}, \tThread ID:{1}", DateTime.Now, Thread.CurrentThread.GetHashCode());
Thread.Sleep(250);
Interlocked.Exchange(ref inTimer, 0);
前一篇:c#串口通信
后一篇:3月3日,牛牛的幼儿园第一天