UUID全局唯一标识符

UUID 是通用唯一识别码(Universally Unique Identifier)的缩写,是一种软件建构的标准,亦为 开放软件基金会 组织在 分布式计算 环境领域的一部分。
UUID 的目的是让 分布式系统 中的所有元素,都能有唯一的辨识资讯,而不需要透过中央控制端来做辨识资讯的指定。如此一来,每个人都可以建立不与其它人冲突的 UUID。在这样的情况下,就不需考虑数据库建立时的名称重复问题。
目前最广泛应用的 UUID,即是微软的 Microsoft's Globally Unique Identifiers (GUIDs),而其他重要的应用,则有 Linux ext2/ext3 档案系统、LUKS 加密分割区、GNOME、KDE、Mac OS X 等等。
UUID是指在一台机器上生成的数字,它保证对在同一时空中的所有机器都是唯一的。通常平台会提供生成的API。按照 开放软件基金会 (OSF)制定的标准计算,用到了以太网卡地址、纳秒级时间、芯片ID码和许多可能的数字
UUID由以下几部分的组合:
(1)当前日期和时间,UUID的第一个部分与时间有关,如果你在生成一个UUID之后,过几秒又生成一个UUID,则第一个部分不同,其余相同。
(2)时钟序列。
(3)全局唯一的IEEE机器识别号,如果有网卡,从网卡MAC地址获得,没有网卡以其他方式获得。
标准的UUID格式如下:
123e4567-e89b-12d3-a456-426655440000
xxxxxxxx-xxxx-Mxxx-Nxxx-xxxxxxxxxxxx
除连字符-外,上面每个字符都是一个十六进制 的数字,共有5个部分组成,第一部分8个,第二部分4个,第三部分4个,第四部分4个,第五部分12个,8-4-4-4-12,一共32个十六进制字符,因此一共是128位, 该结构中包含版本(Version)、变体 (Variant)、时间(Time)、时钟序列(Clock Sequence)、节点(Note)信息(以无符号整型值表示) 。其中,M表示UUID的版本,N表示UUID的变体。
Name
Length (Bytes)
Length (Hex Digits)
Contents
time_low
4
8
integer giving the low 32 bits of the time
time_mid
2
4
integer giving the middle 16 bits of the time
time_hi_and_version
2
4
4-bit "version" in the most significant bits, followed by the high 12 bits of the time
clock_seq_hi_and_res clock_seq_low
2
4
1-3 bit "variant" in the most significant bits, followed by the 13-15 bit clock sequence
node
6
12
the 48-bit node id
变体
为了能兼容过去的UUID,以及应对未来的变化,因此有了变体(Variants)这一概念。目前已知的变体有如下几种:
variant 0:N的格式为0xxx。为了向后兼容预留。
variant 1:10xx。当前正在使用的。
variant 2:11xx。为早期微软GUID预留。
variant 3:111x。为将来扩展预留。目前暂未使用。
版本:
版本用于定义UUID的形成方法, UUID的生成有时间、名称、随机数三种策略,以第9字节(VersionAndTimeHigh)的最高4位表示 ,目前uuid定义有5个版本:
Version 1:基于时间和MAC地址。由于使用了MAC地址,因此能够确保全球唯一性,但是同时也暴露了MAC地址,私密性不够好。
Version 2:DCE安全的UUID DCE(Distributed Computing Environment)安全的UUID和基于时间的UUID算法相同,但会把时间戳的前4位置换为POSIX的UID或GID。这个版本的UUID在实际中较少用到。
Version 3 :基于名字空间(MD5)。 通过计算名字和名字空间的MD5散列值 生成UUID。 相同名字空间中不同名字生成的UUID的唯一性;不同名字空间中的UUID的唯一性;相同名字空间中相同名字的UUID重复生成是相同的。
Version 4 :基于随机数或者伪随机数。虽然是基于随机数,但是重复的可能性可以忽略不计,因此该版本也是被经常使用的版本。
Version 5 : 基于名字空间(SHA1)。跟Version 3类似,但是散列函数使用了SHA1算法。
从UUID的不同版本可以看出,Version 1/2适合应用于分布式计算环境下,具有高度的唯一性;Version 3/5适合于一定范围内名字唯一,且需要或可能会重复生成UUID的环境下;至于Version 4,最好不用
时间戳
时间是一个60位的整型值(除4位版本号外的前8字节),对应UTC(格林尼治时间1582年10月15日午夜始)的100ns时间间隔计数。
对于ver 4和5,该值分别对应一个随机数和一个全局唯一的名称。
时钟序列:
对基于时间的UUID版本,时间序列用于避免因时间向后设置或节点值改变可能造成的UUID重复,对基于名称或随机数的版本同样有用:目的都是为了防止UUID重复。如果前一时钟序列已知,通过自增实现时钟序列值的改变;否则,通过密码学(伪)随机数设置新的时钟序列值。
节点:
对基于时间的UUID版本,节点由48位的单播MAC地址构成。对于没有MAC地址的系统,节点值为一个密码学(伪)随机数(为防止与MAC地址发生碰撞,需设置多播位)。

这些字段对应于版本1和2基于时间的UUIDs,但是相同的8-4-4-12表示用于所有的UUIDs,甚至对于构造不同的UUIDs也是如此。
微软的guid有时会用周围的括号来表示:
{123e4567-e89b-12d3-a456-426655440000}
这种格式不应该与“注册表格式”混淆,“注册表格式”指的是花括号内的格式。
RFC 4122为UUIDs定义了一个统一的资源名称(URN)名称空间。
urn:uuid:123e4567-e89b-12d3-a456-426655440000

UUIDs的二进制编码在系统之间有所不同。许多系统完全以big-endian格式对UUID进行编码。
例如,00112233-4455-6677-8899-aabbccddeeff被编码为字节,以字节为单位,以字节为单位,以字节为单位,以字节为单位。
其他系统,特别是微软在他们的COM/OLE库中对UUIDs进行编组,使用了一个混合的endian格式,其中前三个组件都是little-endian,最后两个是big-endian。
例如,00112233-4455-6677-8899-aabbccddeeff被编码为字节33 22 11 00 5547,688-8899。

UUID是由一组32位数的16进制数字所构成,是故UUID理论上的总数为16^32=2^128,约等于3.4 x 10^38。也就是说若每纳秒产生1兆个UUID,要花100亿年才会将所有UUID用完。
UUID的标准型式包含32个 16进制 数字,以连字号分为五段,形式为8-4-4-4-12的32个字符。示例:
  • 550e8400-e29b-41d4-a716-446655440000
UUID亦可刻意重复以表示同类。例如说 微软 COM 中,所有组件皆必须实现出IUnknown接口,方法是产生一个代表IUnknown的UUID。无论是程序试图访问组件中的IUnknown接口,或是实现IUnknown接口的组件,只要IUnknown一被使用,皆会被参考至同一个ID:00000000-0000-0000-C000-000000000046。

随机产生的UUID(例如说由java.util.UUID类别产生的)的128个比特中,有122个比特是随机产生,4个比特在此版本('Randomly generated UUID')被使用,还有2个在其变体('Leach-Salz')中被使用。利用 生日悖论 ,可计算出两笔UUID拥有相同值的机率约为:
以下是以x=2^122计算出n笔GUID后产生碰撞的机率:
n
机率
68,719,476,736 = 2^36
0.0000000000000004 (4 x 10^-16)
2,199,023,255,552 = 2^41
0.0000000000004 (4 x 10^-13)
70,368,744,177,664 = 2^46
0.0000000004 (4 x 10^-10)
与被陨石击中的机率比较的话,已知一个人每年被陨石击中的机率估计为170亿分之1,也就是说机率大约是0.00000000006 (6 x 10^-11),等同于在一年内置立数十兆笔GUID并发生一次重复。换句话说,每秒产生10亿笔UUID,100年后 只产生一次 重复的机率是50%。如果地球上每个人都各有6亿笔GUID,发生一次重复的机率是50%。
产生重复GUID并造成错误的情况非常低,是故大可不必考虑此问题。
机率也与随机数产生器的质量有关。若要避免重复机率提高,必须要使用基于密码学上的假随机数产生器来生成值才行。

  • 0
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值