iT邦幫忙

第 11 屆 iThome 鐵人賽

DAY 10
2

四、Router 路由器

4.1 概念分析

如果今天有一個需求,希望使用將不同類型的資料,統一的放入 queue ,統一管理。那這樣的情況...

我們來解析一下需求,它想要統一管理所使用的 queue ,所以可以畫出以下的概念圖

https://ithelp.ithome.com.tw/upload/images/20190926/20107551tWt6LNLPqn.png

用白話來說,所有建立的 queue , 都要加入 queue router 之中,但資料要如何個自放到對應的 queue 之中?

試著用 TDD 的方式進行開發,在加入第一個 Test case 時,建立一個 ConcurrentQueue 的 queue 還很順利。

public class QueueRouter
{
    private ConcurrentQueue<int> _queue;

    public void AddQueue(ConcurrentQueue<int> queue){...}
    public void Enqueue(int i){...}
}

但是接下來,建立 ConcurrentQueue 時,就會發現,很多問題浮出水面,AddQueueEnqueue 都會發生類別轉換錯誤的問題。

當然,也可以用硬幹,俗稱暴力破解法來滿足下面的需求。

public class QueueRouter
{
    private ConcurrentQueue<int> _queue;
    private ConcurrentQueue<string> _queueString;

    public void AddQueue(ConcurrentQueue<int> queue){...}
    public void AddQueue(ConcurrentQueue<string> queue){...}
    
    public void Enqueue(int i){...}
    public void Enqueue(string i){...}
}

但是,如果支援的資料類型越來越多,難道要一直在 QueueRouter 之中加入 ConcurrentQueue property 與 method 嗎? 這不但不符合 Open-Close 原則外,也間接增加維護開發的困難。

4.2 資料的封裝

如果將傳入的資料打包,同時有一個標記讓 queue Manager 可以知道新增的資料是屬於那個 queue 的,這種作法的概念圖如下。

Router_payload

public class QueueItem
{
    public string Label { get; set; }
    public object Payload { get; set; }
}

這時,輸入的資料有 Label 可以做為判斷資料類型的依據,如示意圖表示。Router 可以依據 Label 內的資訊來進行歸類的動作。

https://ithelp.ithome.com.tw/upload/images/20190926/20107551A2qdRcsoEP.png

在這個例子中,我們可以先參考下列的程式實作。

public class QueueRouter
{
    private ConcurrentQueue<int> _queue;
    private ConcurrentQueue<string> _strQueue;

    public void AddQueue(ConcurrentQueue<int> queue)
    {
        _queue = queue;
    }

    public void AddQueue(ConcurrentQueue<string> queue)
    {
        _strQueue = queue;
    }

    public void Enqueue(QueueItem item)
    {
        if (item.Label == typeof(int).ToString())
        {
            _queue.Enqueue((int) item.Payload);
        }

        if (item.Label == typeof(string).ToString())
        {
            _strQueue.Enqueue((string) item.Payload);
        }
    }
}

目前寫法,因為是利用 .net 的資料類別,都是繼承 object 的特性實作的。所以會有 Boxing / Unboxing 的吃效能的缺點,但這邊我們先不理它。


上一篇
三、Queue 的應用(5) - 名詞補完:原子性、有序性、可見性
下一篇
四、Router 路由器(2) - Router key
系列文
從零開始土炮MQ30
圖片
  直播研討會
圖片
{{ item.channelVendor }} {{ item.webinarstarted }} |
{{ formatDate(item.duration) }}
直播中

尚未有邦友留言

立即登入留言