当前位置:首页 > 开发 > 互联网 > 正文

分布式uuid生成器- snowflake java 版

发表于: 2014-12-23   作者:blue2048   来源:转载   浏览次数:
摘要: package tools; import java.util.HashSet; import java.util.Set; import java.util.concurrent.ConcurrentHashMap; import java.util.concurrent.CountDownLatch; import java.util.concurrent.atomic.Atom
package tools;

import java.util.HashSet;
import java.util.Set;
import java.util.concurrent.ConcurrentHashMap;
import java.util.concurrent.CountDownLatch;
import java.util.concurrent.atomic.AtomicInteger;

/**
 * User: FR
 * Time: 12/22/14 5:53 PM
 * 测试每秒270w的id生成能力
 */
public class UUID {

    private Long HORIZON_MILLI=1419242747142L;
    private final static Integer SEQUENCE_BITS=12;
    private final static Integer WORK_ID_BITS=5;
    private final static Integer DATA_CENTER_BITS=5;
    private final static Integer MILLI_SECOND_BITS=41;
    private final static Integer MAX_SEQUENCE=-1 ^ (-1<<SEQUENCE_BITS);
    private final static Integer MAX_WORK_ID=-1 ^ (-1<<WORK_ID_BITS);
    private final static Integer MAX_DATA_CENTER_ID=-1 ^ (-1 << DATA_CENTER_BITS);
    private final static Long MAX_MILLISECONDS = -1L ^ (-1L << MILLI_SECOND_BITS);

    private final static Integer MILLI_SHIFT= DATA_CENTER_BITS + WORK_ID_BITS + SEQUENCE_BITS;
    private final static Integer DATA_CENTER_SHIFT= WORK_ID_BITS + SEQUENCE_BITS;
    private final static Integer WORK_ID_SHIFT= SEQUENCE_BITS;


    private Integer work_id=1;
    private Integer data_center_id=1;


    private long sequence = 0;
    private long lastTimestamp=0;

    public UUID(Integer workId, Integer dataCenterId) {
        if((workId & MAX_WORK_ID) == 0){
            throw new RuntimeException("work id is too large");
        }
        if((dataCenterId & MAX_DATA_CENTER_ID) == 0){
            throw new RuntimeException("data center id is too large");
        }
        this.work_id = workId;
        this.data_center_id = dataCenterId;
    }

    public synchronized long nextId(){
        long milliseconds = System.currentTimeMillis();
        if(this.lastTimestamp == milliseconds){
            this.sequence = (this.sequence+1) & MAX_SEQUENCE;
            if(this.sequence == 0){
                milliseconds = tilNextMillis(this.lastTimestamp);
            }
        }else if(milliseconds < this.lastTimestamp){
            throw new RuntimeException("clock wrong");
        }else {
            this.sequence = 0;
        }
        this.lastTimestamp = milliseconds;
        if(((milliseconds-HORIZON_MILLI) & MAX_MILLISECONDS) == 0){
            throw new RuntimeException("time is too large");
        }
        long nextId = ((milliseconds-HORIZON_MILLI)<<MILLI_SHIFT)+(this.data_center_id<<DATA_CENTER_SHIFT)+(this.work_id<<WORK_ID_SHIFT)+this.sequence;
        return nextId;
    }

    private long tilNextMillis(final long lastTimestamp) {
        long timestamp = System.currentTimeMillis();
        while (timestamp <= lastTimestamp) {
            timestamp = System.currentTimeMillis();
        }
        return timestamp;
    }

    public static void main(String[] args) throws InterruptedException {
        final AtomicInteger counter = new AtomicInteger(0);
        final ConcurrentHashMap set = new ConcurrentHashMap();
        final UUID uuid = new UUID(31, 1);
        final CountDownLatch countDownLatch = new CountDownLatch(100);
        final long start = System.currentTimeMillis();
        for (int i=0; i<100; i++){
            new Thread(new Runnable() {
                @Override
                public void run() {
                    while ((System.currentTimeMillis() - start)<6000){
                        long id = uuid.nextId();
                        set.put(id, "");
                        counter.incrementAndGet();
                    }
                    countDownLatch.countDown();
                }
            }).start();
        }
        countDownLatch.await();
        long end = System.currentTimeMillis();
        System.out.println("use time " + (end - start));
        System.out.println(counter.get() + "");
        System.out.println(set.keySet().size());
    }

    public static void main1(String[] args){
        System.out.println(Long.toBinaryString(MAX_MILLISECONDS));
        long start = System.currentTimeMillis();
        UUID uuid = new UUID(31, 1);
        Set<Long> set = new HashSet<Long>();
        while ((System.currentTimeMillis() - start)<6000){
            long id = uuid.nextId();
            set.add(id);
        }
        System.out.println(set.size());
    }
}

 

分布式uuid生成器- snowflake java 版

  • 0

    开心

    开心

  • 0

    板砖

    板砖

  • 0

    感动

    感动

  • 0

    有用

    有用

  • 0

    疑问

    疑问

  • 0

    难过

    难过

  • 0

    无聊

    无聊

  • 0

    震惊

    震惊

编辑推荐
Twitter-Snowflake算法产生的背景相当简单,为了满足Twitter每秒上万条消息的请求,每条消息都必须
Twitter-Snowflake算法产生的背景相当简单,为了满足Twitter每秒上万条消息的请求,每条消息都必须
Twitter-Snowflake算法产生的背景相当简单,为了满足Twitter每秒上万条消息的请求,每条消息都必须
背景 Twitter-Snowflake算法产生的背景相当简单,为了满足Twitter每秒上万条消息的请求,每条消息都
获取【下载地址】 QQ: 313596790 【免费支持更新】 A 代码生成器(开发利器);全部是源码 增删改查的
Quartz是OpenSymphony开源组织在Job scheduling领域又一个开源项目,它可以与J2EE与J2SE应用程序相
一. 背景介绍: Hi,I‘m Ryan,目前网上代码生成器有很多而且功能都很强大、强大的同时也带来操作的
开发快报: 页面打印功能,websocket 强制下线功能,玩转websocket技术 【金牌】 获取【下载地址】
获取【下载地址】 QQ: 313596790 A 代码生成器(开发利器); 增删改查的处理类,service层,mybatis的
sudo gedit /usr/local/hadoop/etc/hadoop/core-site.xml [html] view plain copy <configuratio
版权所有 IT知识库 CopyRight © 2009-2015 IT知识库 IT610.com , All Rights Reserved. 京ICP备09083238号