首頁
編程語言
C語言|JAVA編程
Python編程
網頁編程
ASP編程|PHP編程
JSP編程
數據庫
MYSQL數據庫|SqlServer數據庫
Oracle數據庫|DB2數據庫
您现在的位置: 程式碼之家 >> 編程語言 >  >> 網頁程式設計 >> PHP 程式設計 >> PHP 綜合知識

PHP Memcache 隊列類實現:高併發下的 FIFO 佇列方案

     編輯:PHP 綜合知識

項目背景

在高併發場景下,傳統數據庫寫入易成為瓶頸。基於 Memcache 實現的記憶體隊列,能以極低延遲支撐大吞吐量的異步處理需求。本文分享一個生產級的 memcacheQueue 類,支援先進先出(FIFO)、反向讀取、鎖機制防併發衝突等特性。

核心設計思路

1. 鍵值命名空間

類內部定義四類鍵前綴,避免鍵名衝突:

  • HEAD_KEY:隊列頭指標
  • TAIL_KEY:隊列尾指標
  • VALU_KEY:實際數據存儲
  • LOCK_KEY:分布式鎖標識

2. 指標運算而非數組操作

採用整數遞增/遞減模擬隊列指針,currentHead 和 currentTail 分別指向隊首和隊尾,入隊遞增尾指標,出隊遞增頭指標,O(1) 時間複雜度。

3. 自旋鎖保證原子性

_getLock() 利用 Memcache add 命令的原子特性實現分布式鎖,配合 usleep 退避重試,防止緩存擊穿。

關鍵方法解析

入隊 add($data)

public function add($data) {
    if (!$this->_getLock()) return false;
    if ($this->_isFull()) { $this->_unLock(); return false; }
    $key = $this->queueName . self::VALU_KEY . ($this->currentTail + 1);
    $result = memcache_set(self::$client, $key, $data, MEMCACHE_COMPRESSED, $this->expire);
    if ($result) $this->_changeTail();
    $this->_unLock();
    return $result;
}

出隊 get($length)

支援批量取出並自動刪除,$length > 0 正向讀取,$length < 0 反向讀取:

public function get($length = 0) {
    if (!$this->_getLock()) return false;
    // ... 構建鍵陣列 ...
    $result = @memcache_get(self::$client, $keyArr);
    foreach ($keyArr as $v) @memcache_delete(self::$client, $v, 0);
    $this->_unLock();
    return $result;
}

使用示例

<?php
$queue = new memcacheQueue('order_queue', 3600, ['host' => '127.0.0.1', 'port' => 11211]);
// 生產者
$queue->add(['order_id' => 1001, 'amount' => 99.9]);
// 消費者
$orders = $queue->get(10); // 批量取 10 條
foreach ($orders as $order) { /* 處理訂單 */ }
?>

注意事項與優化建議

  1. 過期時間:構造函數 $expire 建議設為業務允許的最大延遲,避免數據過期丟失。
  2. 隊列長度上限:常量 MAXNUM = 20000 可根據內存調整,防止佔用過多記憶體。
  3. 重試次數:$retryNum = 1000 對應理論並發數,高併發場景可適當增大。
  4. 監控告警:生產環境需監控 getQueueLength(),積壓超閾值時觸發擴容或告警。

總結

此類封裝了分布式隊列的核心邏輯,適合日誌收集、訂單異步處理、消息推送等場景。實際部署時建議搭配 Memcluster 或 Redis Cluster 實現高可用。

  1. 上一篇文章:
  2. 下一篇文章:
Copyright © 程式碼之家 All Rights Reserved