How to set timer queue to zero

3 ビュー (過去 30 日間)
Florian
Florian 2020 年 3 月 13 日
コメント済み: Florian 2020 年 3 月 13 日
Hi all,
I have a program which extensively uses timers to periodically execute tasks. timer spacing is 1s and BusyMode='drop'. Most of the time my call back runs less than one second, but once in a while it takes longer.
I do not want any event to be put in the event queue in case that happens, but rather stick to the 1s intervals all the time if possible. The default queue for 'drop' is 1. Hence: how can I set the queue size to zero so the execution is dropped if my callback takes longer than the timer spacing?
Thanks in advance for your help,
Florian

採用された回答

Geoff Hayes
Geoff Hayes 2020 年 3 月 13 日
Florian - I'm not sure if you can set the queue size to be zero (the documenation doesn't suggest that this is possible). An alternative (though not necessarily practical) approach could be to create a single shot timer that you fire when you complete your callback "work". So if the work takes longer than a second, then you immediately (0 delay) start the timer to do the next iteration. If the work takes less than a second, then you start the timer with a non-zero delay (the difference between 1 and the duration of the work). For example,
function SingleShotTimerTest
k = 1;
timerCallbackStart = 0;
cumulativeTimerCallbackStart = tic;
myTimer = timer('Name','MyTimer', ...
'StartDelay', 1, ...
'ExecutionMode','singleShot', ...
'TimerFcn',{@timerCallback}, ...
'StopFcn', {@stopCallback});
start(myTimer);
function timerCallback(hObject, eventdata)
timerCallbackStart = tic;
timeToPause = rand;
fprintf('timerCallback called at %.3f seconds (pause of %.3f seconds).\n', toc(cumulativeTimerCallbackStart), timeToPause);
pause(timeToPause);
end
function stopCallback(hObject, eventdata)
timeElapsedSeconds = toc(timerCallbackStart);
delaySeconds = 0;
if timeElapsedSeconds < 1
% casting and multiplication and division to avoid warnings
% with StartDelay precision
delaySeconds = double(int32(1000*max(1 - timeElapsedSeconds, 0.001)))/1000;
end
% stop timer after 10 iterations
if k < 10
k = k + 1;
set(myTimer, 'StartDelay', delaySeconds);
start(myTimer);
end
end
end
The above code creates a single-shot timer that fires after one second. The timerCallback fires and pauses for a random (0-1) amount of time. The stop callback then determines the elapsed time (between calls to the stopCallback and the timerCallback) and if that elapsed time is less than one, then the timer is restarted with a delay. If the elapsed time is greater than or equal to one, then timer starts immediately (0 second delay).
I don't know if this will help or it might introduce an overall delay that gets worse the longer the timer runs.
  1 件のコメント
Florian
Florian 2020 年 3 月 13 日
Hi Goeff,
thanks for your answer. Very creative! I'll give it a try.
Best,
Florian

サインインしてコメントする。

その他の回答 (0 件)

カテゴリ

Help Center および File ExchangeLoops and Conditional Statements についてさらに検索

Community Treasure Hunt

Find the treasures in MATLAB Central and discover how the community can help you!

Start Hunting!

Translated by