基於型別的訊息分發實現

2022-04-04 09:57:28 字數 2099 閱讀 8791

在陳碩的github中看到一段非常有意思的**,可以實現根據訊息型別分發到不同的**函式(

link

)。**裡是用的protobuf的反射,本文使用

支援多基類的c++類反射實現

文中的的反射來改寫一下。

首先來定義介面,如果是下面的用例,使用乙個類名為key,callback函式為value的hash表就很容易的實現了:

class

foo :

public

object

{};void

onrecvfoo(object

*foo);

dispatcher.register(

"foo

", onrecvfoo);

但是這樣在onrecvfoo中需要做型別轉換,呼叫register時也需要手動輸入類名字串,容易出錯且麻煩,所以有了如下用例:

void

onrecvfoo(foo

*foo);

dispatcher.register

<

foo>

(onrecvfoo);

下面來分析一下實現,首先定義介面:

class

objectdispatcher

;

register使用帶有模板引數的**函式作為引數,底層訊息系統呼叫onreceive來分發訊息。為了實現註冊分發,需要建立乙個hash表,key是訊息的型別資訊,value是帶有模板引數的**函式。由於value型別並不一致,為了放到hash表中,需要定義乙個共同基類:

class

receivecallback

;

virtual

void

onreceive(object

*obj) =0

;};

然後定義乙個帶模板引數的派生類表示**函式:

template 

<

typename t

>

class

receivecallbackt :

public

receivecallback

virtual

void

onreceive(object

*obj)

protected

: objectcallbackfunc m_func;

};

在dispatcher中新增乙個hash表儲存對應關係,並定義乙個預設**函式用於處理沒有註冊的訊息:

class

objectdispatcher

template

<

typename t

>

void

register(

const

typename receivecallbackt

<

t>

::objectcallbackfunc

&func)

void

onreceive(object

*obj)

const

else

}void

defaultobjectcallback(object

*obj)

private

: typedef std::map

<

const

reflection::classinfo

<

object

>*

, boost::shared_ptr

<

receivecallback

>

>

callbackmap;

callbackmap m_callbacks;

boost::function

<

void

(object *)

>

m_default_callback;

};

這樣的訊息分發機制在一些通訊系統中非常實用。

訊息的分發策略

訊息的分發策略最基礎的就是推,拉機制,這有個最好的理解就是git pull 和 push 在這基礎上制定了有5中訊息的分發策略。支援,不支援 1.發布訂閱 生產者生產多少條訊息,每個消費者就消費多少條訊息 push 2.輪詢分發 訊息數 消費者數 每個消費者消費的訊息數 除不盡剩下條數隨機 3.公平...

Storm的訊息分發策略

1.shuffle grouping 隨機分組 tuple會被隨機分發到所有bolt,每個bolt會得到相同數量的tuple,使得負載均衡。2.fields grouping 按欄位分組 按field分發,只能傳送給相同field的bolt。例如 builder.setbolt mybolt new...

php基於Redis訊息佇列實現的訊息推送的方法

基本知識點 重點用到了以下命令實現我們的訊息推送 邏輯分析 實現 普通任務指令碼 phpforeach user list as item redispushqueue 守護程序執行 nohup php yourpath redispushqueue.php 開啟守護程序執行,修改檔案之後需要從新啟...