当前位置:首页 > PHP教程 > php高级应用 > 列表

PHP实现的服务器一致性hash分布算法示例

发布:smiling 来源: PHP粉丝网  添加日期:2021-10-23 14:25:08 浏览: 评论:0 

这篇文章主要介绍了PHP实现的服务器一致性hash分布算法,结合实例形式分析了php一致性hash分布算法类的具体定义与相关使用技巧,需要的朋友可以参考下。

本文实例讲述了PHP实现的服务器一致性hash分布算法,分享给大家供大家参考,具体如下:

  1. <?php 
  2. /** 
  3.  * 对服务器进行一致性hash分布算法 
  4.  */ 
  5. class HashRing 
  6. { 
  7.   private $servers = array(); 
  8.   private $nodeList = array(); 
  9.   private $nodeHashList = array(); 
  10.   private $nodeTotalNum = 0; 
  11.   private $virtualNodeNum = 32; 
  12.   private $keyHash = ''; 
  13.   public function __construct($servers) 
  14.   { 
  15.     $this->servers = $servers; 
  16.     foreach ($servers as $server) { 
  17.       for ($i = 0; $i < $this->virtualNodeNum; $i++) { 
  18.         $this->nodeList[sprintf("%u", crc32($server.'-'.$i))] = array($server, $i); 
  19.       } 
  20.     } 
  21.     ksort($this->nodeList); 
  22.     $this->nodeHashList = array_keys($this->nodeList); 
  23.   } 
  24.   private function getNodeIndex($key) 
  25.   { 
  26.     $this->keyHash = sprintf("%u", crc32($key)); 
  27.     if ($this->keyHash > end($this->nodeHashList)) { 
  28.       $this->keyHash = $this->keyHash % end($this->nodeHashList); 
  29.     } 
  30.     if ($this->keyHash <= reset($this->nodeHashList)) { 
  31.       return 0; 
  32.     } 
  33.     $this->nodeTotalNum = count($this->nodeHashList); 
  34.     return $this->binaryChopIndex(0, $this->nodeTotalNum); 
  35.   } 
  36.   private function binaryChopIndex($l=0, $r=0) 
  37.   { 
  38.     if ($l < $r) { 
  39.       $avg = intval(($l+$r) / 2); 
  40.       if ($this->nodeHashList[$avg] == $this->keyHash) { 
  41.         return $avg; 
  42.       } elseif ($this->keyHash < $this->nodeHashList[$avg] && ($avg > 0)) { 
  43.         return $this->binaryChopIndex($l, $avg-1); 
  44.       } else { 
  45.         return $this->binaryChopIndex($avg+1, $r); 
  46.       } 
  47.     } else { 
  48.       return $l; 
  49.     } 
  50.   } 
  51.   public function getServersByKey($key, $num=1) 
  52.   { 
  53.     $index = $this->getNodeIndex($key); 
  54.     $server = $this->nodeList[$this->nodeHashList[$index]]; 
  55.     if ($num == 1) { 
  56.       return $server[0]; 
  57.     } 
  58.     if ($num >= count($this->servers)) { 
  59.       $num = count($this->servers); 
  60.     } 
  61.     $result = array($server[0]); 
  62.     for ($i=$index+1; true; $i++) { 
  63.       if ($i >= $this->nodeTotalNum) { 
  64.         $i = 0; 
  65.       } 
  66.       $nextServer = $this->nodeList[$this->nodeHashList[$i]]; 
  67.       if (!in_array($nextServer[0], $result)) { 
  68.         $result[] = $nextServer[0]; 
  69.       } 
  70.       if (count($result) == $num) { 
  71.         break; 
  72.       } 
  73.     } 
  74.     return $result; 
  75.   } 
  76. } 
  77. //示例 
  78. $servers = array( 
  79.   '127.0.0.1:11211', 
  80.   '127.0.0.1:11212', 
  81.   '127.0.0.1:11213', 
  82.   '127.0.0.1:11214', 
  83.   '127.0.0.1:11215' 
  84. ); 
  85. $obj = new HashRing($servers); 
  86. $servers = $obj->getServersByKey('testkey', 2); 
  87. print_r($servers); 
  88. echo "\n"; 

运行结果:

  1. Array 
  2. ( 
  3.     [0] => 127.0.0.1:11214 
  4.     [1] => 127.0.0.1:11211 
  5. )

Tags: PHP服务器一致性 hash分布

分享到: