一致性哈希算法 Java 实现
发布于: 2020 年 07 月 09 日
一致性哈希算法是当前较主流的分布式哈希表协议之一,它对简单哈希算法进行了修正,解决了热点(hotPot)问题。
一致性哈希算法

基于虚拟节点的一致性哈希算法

一致性哈希算法Java实现
基于虚拟节点的一致性哈希算法实现。
public class ConsistentHash {    private List<String> nodeList;    private int virtualNodeDepth;    private SortedMap<Integer, String> nodeMap = new TreeMap<>();    public ConsistentHash(List<String> nodeList) {        this(nodeList, 10);    }    public ConsistentHash(List<String> nodeList, int virtualNodeDepth) {        this.nodeList = nodeList;        this.virtualNodeDepth = virtualNodeDepth;        if (virtualNodeDepth < 1) {            this.virtualNodeDepth = 1;        }        this.init();    }    public String doHash(String key) {        int hashValue = getHash(key);        SortedMap<Integer, String> subMap = nodeMap.tailMap(hashValue);        String virtualNode;        if(subMap.isEmpty()){            Integer i = nodeMap.firstKey();            virtualNode = nodeMap.get(i);        }else{            Integer i = subMap.firstKey();            virtualNode = subMap.get(i);        }        if(!StringUtils.isEmpty(virtualNode)){            return virtualNode.substring(0, virtualNode.indexOf("##"));        }        return null;    }    private int getHash(String str) {        final int p = 16777619;        int hash = (int) 2166136261L;        for (int i = 0; i < str.length(); i++) {            hash = (hash ^ str.charAt(i)) * p;        }        hash += hash << 13;        hash ^= hash >> 7;        hash += hash << 3;        hash ^= hash >> 17;        hash += hash << 5;                if (hash < 0) {            hash = Math.abs(hash);        }        return hash;    }    private void init() {        String virtualNodeKey;        for (String node : nodeList) {            for (int index = 0; index < virtualNodeDepth; index++) {                virtualNodeKey = node + "##" + index;                int hashValue = getHash(virtualNodeKey);                nodeMap.put(hashValue, virtualNodeKey);            }        }    }}
计算标准差:
public class StandardDeviation {    private List<Integer> numbers;    public StandardDeviation(List<Integer> numbers) {        this.numbers = numbers;    }    public double getStandardDevition() {        double sum = 0;        int num = numbers.size();        for (int i = 0; i < num; i++) {            double average = (double) numbers.get(i) - getAverage();            sum += Math.sqrt((average * average));        }        return (sum / (num - 1));    }    public double getAverage() {        int sum = 0;        int num = numbers.size();        for (int i = 0; i < num; i++) {            sum += numbers.get(i);        }        return (double) (sum / num);    }}
测试类:
public static final void main(String[] args) {        List<String> nodeList = new ArrayList<>();        nodeList.add("192.168.1.2");        nodeList.add("192.168.1.3");        nodeList.add("192.168.1.5");        nodeList.add("192.168.1.6");        ConsistentHash consistentHash = new ConsistentHash(nodeList);        Map<String, Integer> result = new HashMap<>();        for (int index = 0; index < 1000000; index++) {            String nodeKey = consistentHash.doHash(String.valueOf(index));            Integer count = result.get(nodeKey);            if (count == null) {                count = 1;            } else {                count++;            }            result.put(nodeKey, count);        }        System.out.println("result : " + result);        List<Integer> numbers = new ArrayList<>();        for (Map.Entry<String, Integer> entry : result.entrySet()) {            numbers.add(entry.getValue());        }        StandardDeviation standardDeviation = new StandardDeviation(numbers);        double standardDevition = standardDeviation.getStandardDevition();        System.out.println("standardDevition : " + standardDevition);    }
结果是:
result : {192.168.1.3=206917, 192.168.1.2=169495, 192.168.1.5=237154, 192.168.1.6=386434}standardDevition : 90956.0
 划线
   评论
  复制
发布于: 2020 年 07 月 09 日 阅读数: 31
 
 dapaul
  关注 
还未添加个人签名 2018.09.18 加入
还未添加个人简介
 
 
  
  
 
 
 
  
  
  
  
  
  
  
  
    
评论