timer做爲其計時器:git
erlang的計時器timer是經過一個惟一的timer進程實現的,該進程是一個gen_server,用戶經過timer:send_after和timer:apply_after在指定時間間隔後收到指定消息或執行某個函數,每一個用戶的計時器都是一條記錄,保存在timer的ets表timer_tab中,timer的時序驅動經過gen_server的超時機制實現。若同時使用timer的用戶過多,則timer將響應不過來,成爲瓶頸。github
更好的方法是使用erlang的原生計時器erlang:send_after和erlang:start_timer,它們把計時器附着在進程本身身上。app
看了段timer的源碼,以下:函數
schedule_cast(Msg, Default, Timers) -> %% Cancel the old timer... TRef = proplists:get_value(Msg, Timers), timer:cancel(TRef), %% Lookup the interval... IntervalKey = list_to_atom(atom_to_list(Msg) ++ "_interval"), Interval = sync_utils:get_env(IntervalKey, Default), %% Schedule the call... {ok, NewTRef} = timer:apply_after(Interval, gen_server, cast, [?SERVER, Msg]), %% Return the new timers structure... lists:keystore(Msg, 1, Timers, {Msg, NewTRef}).
這裏的 timer:apply_after/4 這裏爲什麼要這麼寫? timer:apply_after(Time, Module, Function, Arguments) -> {ok, TRef} | {error, Reason}atom
沒有去調用timer:send_after 查看API後,apply_after是函數形式,send_after是發消息,查看timer的源碼以後,發現send_after就是調用apply_after,只是兩種寫法罷了。
timer的源碼連接:見 https://github.com/zhongwencool/otp/blob/maint/lib/stdlib/src/timer.erl
從學貴有恆的博客中,看到了下面的圖:
這是根據timer源碼,畫的流程圖,
timer的進程都是經過一個惟一的timer進程實現的,該進程是一個gen_server。建議使用erlang::send_after和erlang:start_timer,它們把計時器附着在進程本身身上.