更優雅的延遲執行實現 環形佇列

2021-09-02 19:32:19 字數 781 閱讀 6760

在做業務時經常遇到某些一次性的延遲需求,比如新聞的定時發布,過了乙個時間閾值後某個任務的狀態置為超時或觸發某個介面。

之前實現這種一次性的延遲需求基本會有3種思路。

(1)執行緒輪詢掃庫

(2)timer類

(3)定時框架quartz

這三種方案都存在各自的問題

對於「執行緒輪詢掃庫」,效能開銷巨大,實時性差

對於「timer類」來說,假如專案重啟,之前設定的定時就蕩然無存

對於「定時框架quartz」雖然支援dbstore,但是框架太過於重量級。

如何優雅而又高效的實現乙個延遲任務呢?前不久看到一篇文章  ,似乎提供了乙個不錯的解法。

按照思路我自己實現了乙個環形佇列,

這篇文章只是提出乙個解決的思路,但是有幾個問題並未說明

2.大規模集群環境下如何保證正常執行? 解決方案:這點非常關鍵,在集群條件下,如果專案重啟,那麼乙個任務就會被執行n次,此時我想到的解決方案是根據某種規則進行資料的初始化,比如某個集群裡有3臺機器編號分別為1,2,3,那麼每台在initdata的時候分別載入 taskid%3-機器編號=0 的任務。當然我提出的這種方案並不是最好的,他同樣會存在熱點問題,會使某台機器上執行的task比其他機器上多,大體解決思路可以參考一些負載均衡策略。

另外糾正下文章最後說「開源的mq好像都不支援延遲訊息」這句話,據我所知阿里的rocketmq是支援延遲訊息的。

APP效能優化系列 更優雅的延遲方案(四)

在我們日常處理一些耗時任務的時候,有很多的方案,比如 1.可以通過handler sendmessagedelayed 達到延遲載入。原理 將訊息加入佇列中,然後messagequeue會根據延時的時間進行佇列的排序,時間最短的在前,如果沒有要執行的,就進行阻塞,阻塞的時間為最先要執行的任務的等待時...

佇列和環形佇列的實現

1 基本介紹 2 陣列模擬佇列 public class arrayqueuedemo catch exception e break case h trycatch exception e break case e scanner.close flag false break default br...

環形佇列的實現原理

環形佇列是乙個首尾相連的fifo 命名管道 的資料結構,它採用陣列的線性空間。它能很快知道佇列是否為滿或者為空,也能很快的訪問資料。原理 記憶體上沒有環形結構,因此環形佇列利用陣列的線性空間來實現。當資料到了尾部時,它將轉回到0位置來處理。這個轉回操作通過取模來執行。構造 邏輯上,將陣列q 0 與q...