我希望每10ms運行一次週期性erlang進程(基於掛鐘時間),10ms應該儘可能精確;什麼應該是實施它的正確方法?如何以精確時間週期(即10ms)週期性運行Erlang進程
5
A
回答
6
如果你想真正可靠和準確的週期性過程中,你應該使用erlang:monotonic_time/0,1
依靠實際的掛鐘時間。如果您使用Stratus3D的answer中的方法,您最終會落後。
start_link(Period) when Period > 0, is_integer(Period) ->
gen_server:start_link({local, ?SERVER}, ?MODULE, Period, []).
...
init(Period) ->
StartT = erlang:monotonic_time(millisecond),
self() ! tick,
{ok, {StartT, Period}}.
...
handle_info(tick, {StartT, Period} = S) ->
Next = Period - (erlang:monotonic_time(millisecond)-StartT) rem Period,
_Timer = erlang:send_after(Next, self(), tick),
do_task(),
{ok, S}.
可以在殼體試驗:
spawn(fun() ->
P = 1000,
StartT = erlang:monotonic_time(millisecond),
self() ! tick,
(fun F() ->
receive
tick ->
Next = P - (erlang:monotonic_time(millisecond)-StartT) rem P,
erlang:send_after(Next, self(), tick),
io:format("X~n", []),
F()
end
end)()
end).
0
如果你真的想要儘可能精確,並且你確定你的任務比你想要執行的時間間隔更短,那麼你可以有一個長時間運行的進程,而不是每隔10ms產生一個進程。 Erlang可以每隔10ms產生一個新進程,但除非有理由不能重複使用相同的進程,否則通常不值得開銷(儘管它很少)。
我會做這樣的事情在OTP gen_server:作爲gen_server運行
periodic_task:start_link().
只要(如果它崩潰所以纔會父:
-module(periodic_task).
... module exports
start_link() ->
gen_server:start_link({local, ?SERVER}, ?MODULE, [], []).
... Rest of API and other OTP callbacks
init([]) ->
Timer = erlang:send_after(0, self(), check),
{ok, Timer}.
handle_info(check, OldTimer) ->
erlang:cancel_timer(OldTimer),
Timer = erlang:send_after(10, self(), check),
do_task(), % A function that executes your task
{noreply, Timer}.
然後開始像這樣的gen_server過程,因爲它們被鏈接),功能do_task/0
幾乎每10毫秒執行一次。請注意,這不會完全準確。執行時間會有一個漂移。實際的時間間隔將是10ms +接收定時器消息所需的時間,取消舊定時器並啓動新定時器。
如果你想每隔10ms開始一個單獨的進程,你可以讓do_task/0
產生一個進程。請注意,這會增加額外的開銷,但不一定會使得派生之間的間隔不太準確。
我的例子,從這個答案採取:What's the best way to do something periodically in Erlang?
相關問題
- 1. ARM週期精確模擬器
- 2. 時間延遲/延遲估計非週期性信號(和週期性信號)
- 3. Android:以不同的睡眠時間間隔運行週期性任務
- 4. 周的C#日期時間
- 5. 運行任務週期性(每天一次/每週一次)
- 6. 如何在Firebase JobDispatcher中設置週期性任務的週期?
- 7. 長時間運行的線程+生命週期
- 8. 運行時錯誤週期FLASH CS5
- 9. 執行週期性同步時出錯
- 10. 100ms週期的便攜式週期性定時器
- 11. 加快Erlang編輯,編譯,運行/調試周期
- 12. 在WebJobs長時間運行的進程中正確運行ADAL的AuthenticationContext生命週期管理
- 13. 確定日期是週日/週末java
- 14. 在週期性運行的線程中自動執行代碼
- 15. 以可變採樣率對週期性數據進行平均
- 16. PHP日期時間:獲取日期基於月,周和一週的日期
- 17. 在iOS8上以後臺模式運行週期性任務
- 18. mybatis批處理執行期間的週期性沖洗
- 19. 如何使用reactjs在週期性時間渲染數據
- 20. 如何存儲週期性時間窗口
- 21. 時間間隔週期在SQL
- 22. Java:使用定時器週期性地運行一個方法
- 23. 週期性變化HTML體在運行時的內容 -
- 24. 如何在設定的時鐘週期內運行模擬
- 25. 進口週期RSA 8.5
- 26. 如何計算週期性數字?
- 27. 如何解決球體的週期性?
- 28. 我如何處理週期性結算?
- 29. 如何執行持續的,變化的時間週期
- 30. 貝寶週期性+購買
使用這種方法的好處是,小不可避免的錯誤不會在時間積累。 – Pascal