zoukankan      html  css  js  c++  java
  • erlang supervisor simple_one_for_one实例

    http://www.cnblogs.com/little-ant/p/3196201.html

    simple_one_for_one vs one_for_one:

    相同点:

    这种Restart Strategy和one_for_one基本相同(即当一个child process挂掉后,仅仅重启该child process 而不影响其他child process)。

    异同点:

    1, simple_one_for_one supvisor启动时不会启动任何子进程,所有子进程都只能通过调用 supervisor:start_child(Sup, Args) 来动态启动。

    2, simple_one_for_one supvisor持有child process的定义,并有一个dict存放数据, 其实就是如干个child process,共享一份数据。

    3, 一个simple_one_for_one supervisor只有一个(single)simple_one_for_one的定义, 也就是说它只能生产出一种类型worker process。

    supervisor:start_child(Sup, Args) :

        Sup:  Supervisor的Pid或者registered Name.

        Args: 当supervisor的类型是simple_one_for_one时,Args会追加到spec的参数中。

    例如:

    复制代码
    -module(simple_sup).
    -behaviour(supervisor).
    
    -export([start_link/0]).
    -export([init/1]).
    
    start_link() ->
        supervisor:start_link({local,?MODULE}, ?MODULE, []).
    
    init(_Args) ->
      {M, F, A} = _Args,
        {ok, {{simple_one_for_one, 0, 1},
              [{M, {M, F, A},
                temporary, brutal_kill, worker, [M]}]}}.
    复制代码

    调用supervisor:start_child(simple_sup, Args)后,最终启动子进程的代码会是:apply(M, F, A++Args).

    调用supervisor:start_child(Sup, Args)可能会遇到的错误:

    1, noproc: 可能的原因是在调用supervisor:start_link时没写参数{local, ?MODULE},即上面代码红色部分,此时进程Sup并不存在,所以会产生

                     noproc错误。

    2,undef: 可能的原因是A++Args后,与child process的start_link函数参数不一致。

    实例代码:

         实例包含两部分,一是监控普通进程(normal_process.erl),二是监控gen_server进程(gen_server_process.erl)。

    common.hrl

    %%-define(CALL, normal_process).
    -define(CALL, gen_server_process).

    simple_sup.erl

    复制代码
    -module(simple_sup).
    -behaviour(supervisor).
    
    -export([start_link/0]).
    -export([init/1]).
    
    -include("common.hrl").
    
    start_link() ->
        supervisor:start_link({local, ?MODULE}, simple_sup, []).
    
    init(_Args) ->
        {ok, {{simple_one_for_one, 0, 1}, 
              [{?CALL, {?CALL, start_link, []},
              temporary, brutal_kill, worker, [?CALL]}]}}.
    复制代码

    normal_process.erl

    复制代码
    -module(normal_process).
    
    -export([start_link/0, start_loop/1]).
    
    start_link() ->
        proc_lib:start_link(?MODULE, start_loop, [self()]).
    
    start_loop(Parent) ->
        proc_lib:init_ack(Parent, {ok, self()}),
        loop().
    
    loop() ->
        receive
            Args ->
                io:format("~p~n", [Args])
        end.
    复制代码

    gen_server_process.erl

    复制代码
    -module(gen_server_process).
    -behaviour(gen_server).
    -export([start_link/0]).
    
    %% gen_server callbacks
    -export([init/1, handle_call/3, handle_cast/2, handle_info/2,
             terminate/2, code_change/3]).
    
    %% interface
    -export([start/0, stop/0, echo/1]).
    
    %% interface implement
    start()      -> start_link().
    stop()       -> gen_server:call(?MODULE, stop).
    echo(String) -> gen_server:call(?MODULE, {echo, String}).
    
    %% gen_server callbacks implement
    start_link() -> gen_server:start_link({local,?MODULE}, ?MODULE, [], []).
    
    init([]) ->
        {ok, 0}. 
    
    handle_call({echo, String}, _From, Tab) ->  
        Reply = String,
        {reply, Reply, Tab};
    
    handle_call(stop, _From, Tab) ->
        {stop, normal, stopped, Tab}.
    
    handle_cast(_Msg, State) -> {noreply, State}.
    handle_info(_Info, State) -> {noreply, State}.
    terminate(_Reason, _State) -> ok. 
    code_change(_OldVsn, State, _Extra) -> {ok, State}.
    复制代码

    编译命令:

    c(simple_sup).
    c(normal_process).
    c(gen_server_process).

    测试命令:

    simple_sup:start_link().
    supervisor:start_child(simple_sup, []).

    测试通过start_child启动普通进程:

    修改common.hrl:-define(CALL, normal_process). 执行编译命令 + 测试命令。

    测试通过start_child启动gen_server进程:

    修改common.hrl:-define(CALL, gen_server_process). 执行编译命令 + 测试命令。

  • 相关阅读:
    2. Add Two Numbers
    1. Two Sum
    22. Generate Parentheses (backTracking)
    21. Merge Two Sorted Lists
    20. Valid Parentheses (Stack)
    19. Remove Nth Node From End of List
    18. 4Sum (通用算法 nSum)
    17. Letter Combinations of a Phone Number (backtracking)
    LeetCode SQL: Combine Two Tables
    LeetCode SQL:Employees Earning More Than Their Managers
  • 原文地址:https://www.cnblogs.com/fvsfvs123/p/4243734.html
Copyright © 2011-2022 走看看