有时我们的服务会从多个其他子服务接收请求,不同类型的请求频率相差比较大,如果采用一个集中的队列,对到来的各个请求排队分发处理,则会出现繁忙的请求占据了队列的大部分,比较闲的请求到达后排在队尾,很长时间才会得到处理机会,出现不必要的延迟加大。这种情况下如果要加强各类型请求的响应及时性,可以采用优先队列,按照请求类型的频率加预计排队时间指定优先级,也可以使用公平队列,公平地处理各个类型的消息。
完全公平队列的原理很简单:为各个类型请求维护一个单独的子队列,维护一个链表包含所有子队列的指针;接收到请求后,根据类型找到其子队列并插入子队列末尾;分发线程分发请求时,依次遍历链表中的子队列并将此子队列移动到链表尾,如果子队列有请求,则将请求投递到工作线程执行,否则一直遍历,直到链表中的所有子队列都查询过,如果还是没有请求待处理,则进入等待。
按照上面描述,可以如下实现:unordered_map 用来保存类型和对应的子队列,list 维护着子队列的指针用来遍历。
#ifndef __COMPLETE_FAIR_QUEUE_H_
#define __COMPLETE_FAIR_QUEUE_H_
#include <list>
#include <unordered_map>
#include <mutex>
#include <condition_variable>
template <
class _Key,
class _Val,
class _Hash = std::hash<_Key>,
class _Pred = std