GoLang中生成UUID唯一标识的实现


Posted in Golang onMay 08, 2021

1、什么是UUID

UUID简介

通用唯一识别码(英语:Universally Unique Identifier,简称UUID)是一种软件建构的标准,亦为自由软件基金会组织在分散式计算环境领域的一部份。

UUID的目的,是让分散式系统中的所有元素,都能有唯一的辨识信息,而不需要通过中央控制端来做辨识信息的指定。

如此一来,每个人都可以创建不与其它人冲突的UUID。

在这样的情况下,就不需考虑数据库创建时的名称重复问题。目前最广泛应用的UUID,是微软公司的全局唯一标识符(GUID),而其他重要的应用,则有Linux ext2/ext3文件系统、LUKS加密分区、GNOME、KDE、Mac OS X等等。

2、Go中现有的UUID第三方生成办法

目前,golang中的uuid还没有纳入标准库,我们使用github上的开源库:

go get -u github.com/satori/go.uuid

使用:

package main 
import (
    "fmt"
    "github.com/satori/go.uuid"
)
 
func main() {
   id := uuid.NewV4()
   ids := id.String()
}

3、自定义的 UUIDGenerator实现

功能:

UUIDGenerator 可以生成全局唯一的字符串形式的ID,ID由两部分构成,一部分是用户指定的前缀,另一部分是数字,数字的最大值为 4294967295;

UUIDGenerator 可以生成全局唯一的无符号整形数字,数字范围 0- 4294967295

代码

package utils 
import "fmt"
 
const (
    MAXUINT32 = 4294967295
    DEFAULT_UUID_CNT_CACHE = 512
)
 
type UUIDGenerator struct {
    Prefix       string
    idGen        uint32
    internalChan chan uint32
}
 
func NewUUIDGenerator(prefix string) *UUIDGenerator {
    gen := &UUIDGenerator{
        Prefix:       prefix,
        idGen:        0,
        internalChan: make(chan uint32, DEFAULT_UUID_CNT_CACHE),
    }
    gen.startGen()
    return gen
}
 
//开启 goroutine, 把生成的数字形式的UUID放入缓冲管道
func (this *UUIDGenerator) startGen() {
    go func() {
        for {
            if this.idGen == MAXUINT32 {
                this.idGen = 1
            } else {
                this.idGen += 1
            }
            this.internalChan <- this.idGen
        }
    }()
}
 
//获取带前缀的字符串形式的UUID
func (this *UUIDGenerator) Get() string {
    idgen := <-this.internalChan
    return fmt.Sprintf("%s%d", this.Prefix, idgen)
}
 
//获取uint32形式的UUID
func (this *UUIDGenerator) GetUint32() uint32 {
    return <-this.internalChan
}

测试用例:

package utils 
import (
    "testing"
    "fmt"
)
 
func TestUUIDGenerator(t *testing.T) {
    //新建UUIDGennerator
    UUIDFactory := NewUUIDGenerator("idtest")
 
    //获取UUID
    for i:= 0; i < 50; i++{
        fmt.Println(UUIDFactory.Get())
    }
 
    //获取uint32 形式的UUID
    for i := 0; i < 50; i++{
        fmt.Println(UUIDFactory.GetUint32())
    }
}

结果

idtest1

idtest2

idtest3

idtest4

idtest5

6

7

8

9

10

PASS

补充:golang 的 UUID 使用

安装

go get github.com/satori/go.uuid

使用

几种 UUID 的产生方式:

Version 1, based on timestamp and MAC address (RFC 4122)
Version 2, based on timestamp, MAC address and POSIX UID/GID (DCE 1.1)
Version 3, based on MD5 hashing (RFC 4122)
Version 4, based on random numbers (RFC 4122)
Version 5, based on SHA-1 hashing (RFC 4122)

示例代码:

package main
import (
    "fmt"
    "github.com/satori/go.uuid"
)
func main() {
    // Creating UUID Version 4
    // panic on error
    u1 := uuid.Must(uuid.NewV4())
    fmt.Printf("UUIDv4: %s\n", u1)
    // or error handling
    u2, err := uuid.NewV4()
    if err != nil {
        fmt.Printf("Something went wrong: %s", err)
        return
    }
    fmt.Printf("UUIDv4: %s\n", u2)
    // Parsing UUID from string input
    u2, err := uuid.FromString("6ba7b810-9dad-11d1-80b4-00c04fd430c8")
    if err != nil {
        fmt.Printf("Something went wrong: %s", err)
    }
    fmt.Printf("Successfully parsed: %s", u2)
}

以上为个人经验,希望能给大家一个参考,也希望大家多多支持三水点靠木。如有错误或未考虑完全的地方,望不吝赐教。

Golang 相关文章推荐
win10下go mod配置方式
Apr 25 Golang
golang 在windows中设置环境变量的操作
Apr 29 Golang
解决Golang中goroutine执行速度的问题
May 02 Golang
解决goland 导入项目后import里的包报红问题
May 06 Golang
Go语言基础函数基本用法及示例详解
Nov 17 Golang
Go语言特点及基本数据类型使用详解
Mar 21 Golang
golang使用map实现去除重复数组
Apr 14 Golang
golang语言指针操作
Apr 14 Golang
Go调用Rust方法及外部函数接口前置
Jun 14 Golang
GoFrame基于性能测试得知grpool使用场景
Jun 21 Golang
go goth封装第三方认证库示例详解
Aug 14 Golang
Go gorilla securecookie库的安装使用详解
Aug 14 Golang
聊聊golang中多个defer的执行顺序
May 08 #Golang
Golang全局变量加锁的问题解决
golang 实现并发求和
May 08 #Golang
golang中的并发和并行
May 08 #Golang
关于golang高并发的实现与注意事项说明
May 08 #Golang
基于Golang 高并发问题的解决方案
May 08 #Golang
使用golang编写一个并发工作队列
May 08 #Golang
You might like
linux系统上支持php的 iconv()函数的方法
2011/10/01 PHP
php封装的mysqli类完整实例
2016/10/18 PHP
php模仿qq空间或朋友圈发布动态、评论动态、回复评论、删除动态或评论的功能(中)
2017/06/11 PHP
javascript preload&amp;lazy load
2010/05/13 Javascript
SlideView 图片滑动(扩展/收缩)展示效果
2010/08/01 Javascript
浅谈jQuery异步对象(XMLHttpRequest)
2014/11/17 Javascript
js使用递归解析xml
2014/12/12 Javascript
JavaScript中constructor()方法的使用简介
2015/06/05 Javascript
javascript实现简单的进度条
2015/07/02 Javascript
JavaScript 对象详细整理总结
2016/09/29 Javascript
详解在Angularjs中ui-sref和$state.go如何传递参数
2017/04/24 Javascript
关于Vue.nextTick()的正确使用方法浅析
2017/08/25 Javascript
基于webpack4搭建的react项目框架的方法
2018/06/30 Javascript
vue路由对不同界面进行传参及跳转的总结
2019/04/20 Javascript
vue点击按钮动态创建与删除组件功能
2019/12/29 Javascript
Python循环语句之break与continue的用法
2015/10/14 Python
python3.X 抓取火车票信息【修正版】
2018/06/19 Python
kafka监控获取指定topic的消息总量示例
2019/12/23 Python
Python包,__init__.py功能与用法分析
2020/01/07 Python
简单了解Django ORM常用字段类型及参数配置
2020/01/07 Python
TensorFlow自定义损失函数来预测商品销售量
2020/02/05 Python
Python基于字典实现switch case函数调用
2020/07/22 Python
配件采购员岗位职责
2013/12/03 职场文书
幼儿园六一儿童节文艺汇演主持词
2014/03/21 职场文书
战友聚会主持词
2014/04/02 职场文书
关于孝道的演讲稿
2014/05/21 职场文书
技能比武方案
2014/05/21 职场文书
健康教育评估方案
2014/05/25 职场文书
酒后驾车标语
2014/06/30 职场文书
文员岗位职责范本
2015/04/16 职场文书
老乡聚会通知
2015/04/23 职场文书
2015小学音乐教师个人工作总结
2015/07/21 职场文书
2016年12月份红领巾广播稿
2015/12/21 职场文书
德劲DE1108畅想
2021/04/22 无线电
Redis高级数据类型Hyperloglog、Bitmap的使用
2021/05/24 Redis
mybatis源码解读之executor包语句处理功能
2022/02/15 Java/Android