ULID(Universally Unique Lexicographically Sortable Identifier)是一种用于生成全局唯一、可按字典序排序的标识符的格式。ULID结合了时间戳和随机数的特性,旨在提供高性能、低碰撞、可排序和易读的标识符。
ULID的主要特点包括:
- 全局唯一性:通过结合时间戳和随机数的方式,ULID可以生成全局唯一的标识符,避免了碰撞的可能性。
- 按字典序排序:ULID生成的标识符是按照时间戳先后顺序排列的,可以方便地进行排序和比较。
- 性能优化:ULID的设计旨在提供高性能的生成过程,适用于需要频繁生成标识符的场景。
- 可读性:ULID采用了基于Crockford's Base32编码的方式,生成的标识符具有一定的可读性,不同于传统的UUID。
ULID的格式通常由 48 位长度组成,其中包含前缀时间戳和随机数部分。ULID的生成过程包括获取当前时间戳(以毫秒为单位)、生成随机数部分、将时间戳和随机数合并,并进行Base32编码等步骤。
为什么使用ULID:
- 全局唯一性:ULID生成的标识符在分布式系统中具有全局唯一性,可以避免碰撞风险。
- 排序能力:ULID生成的标识符可以按照时间戳顺序排序,方便数据库索引和查询操作。
- 性能优化:ULID的设计考虑了高性能的生成过程,适用于需要频繁生成标识符的场景。
- 可读性:ULID生成的标识符相对于传统的UUID更具可读性,便于人类阅读和理解。
ULID作为一种全局唯一、可排序、高性能的标识符生成方案,适用于分布式系统、数据库主键、日志记录等各种场景,为应用程序提供了一种轻量级且有效的标识符生成方式。
在 PowerShell 中,你可以使用以下命令生成 Windows 的 ULID(Universally Unique Lexicographically Sortable Identifier):
powershellCopy CodeAdd-Type -TypeDefinition @"
using System;
public class Ulid
{
private static readonly DateTime UnixEpoch = new DateTime(1970, 1, 1, 0, 0, 0, DateTimeKind.Utc);
private static readonly Random Random = new Random();
public static string NewUlid()
{
byte[] random = new byte[10];
Random.NextBytes(random);
long milliseconds = (DateTime.UtcNow - UnixEpoch).Ticks / 10000;
byte[] time = BitConverter.GetBytes(milliseconds);
Array.Reverse(time);
byte[] ulidBytes = new byte[16];
Buffer.BlockCopy(time, 2, ulidBytes, 0, 6);
Buffer.BlockCopy(random, 0, ulidBytes, 6, 10);
return EncodeBase32(ulidBytes);
}
private static string EncodeBase32(byte[] data)
{
const string base32Chars = "0123456789ABCDEFGHJKMNPQRSTVWXYZ";
const int size = 13;
var sb = new System.Text.StringBuilder(size);
int buffer = data[0];
int next = 1;
int bitsLeft = 8;
while (bitsLeft > 0 || next < data.Length)
{
if (bitsLeft < 5)
{
if (next < data.Length)
{
buffer <<= 8;
buffer |= data[next++] & 0xFF;
bitsLeft += 8;
}
else
{
int pad = 5 - bitsLeft;
buffer <<= pad;
bitsLeft += pad;
}
}
int index = 0x1F & (buffer >> (bitsLeft - 5));
bitsLeft -= 5;
sb.Append(base32Chars[index]);
}
return sb.ToString();
}
}
"@
[Ulid]::NewUlid()
运行以上 PowerShell 命令,将会生成一个 ULID 格式的字符串作为输出。这个 ULID 是根据当前时间和随机数生成的全局唯一标识符,符合 ULID 格式规范。
PowerShell 中,注册表路径应该使用根键的名称来指定,而不是直接指向文件系统路径。
尝试使用以下命令来获取 MachineGuid
的值:
Get-ItemProperty -Path "HKLM:\SOFTWARE\Microsoft\Cryptography" | Select-Object -Property MachineGuid
这条命令中,我们将注册表路径改为 HKLM:\SOFTWARE\Microsoft\Cryptography
,并使用 Get-ItemProperty
命令来获取 MachineGuid
的值。这样应该就能成功读取注册表中的 MachineGuid
值了。
需要生成 48 位长度的 Windows ULID,可以使用以下 PowerShell 脚本:
powershellCopy Codefunction New-Ulid {
$base32Chars = "0123456789ABCDEFGHJKMNPQRSTVWXYZ"
$timeBytes = [BitConverter]::GetBytes([DateTime]::UtcNow.Ticks)
$randomBytes = [byte[]]::new(10)
[System.Security.Cryptography.RNGCryptoServiceProvider]::Create().GetBytes($randomBytes)
$ulidBytes = $timeBytes[6..11] + $randomBytes
$sb = [System.Text.StringBuilder]::new()
$buffer = $ulidBytes[0]
$next = 1
$bitsLeft = 8
while ($bitsLeft -gt 0 -or $next -lt 16) {
if ($bitsLeft -lt 5) {
if ($next -lt 16) {
$buffer = $buffer -shl 8
$buffer = $buffer -bor $ulidBytes[$next]
$next += 1
$bitsLeft += 8
} else {
$pad = 5 - $bitsLeft
$buffer = $buffer -shl $pad
$bitsLeft += $pad
}
}
$index = 0x1F -band ($buffer -shr ($bitsLeft - 5))
$bitsLeft -= 5
$sb.Append($base32Chars[$index])
}
return $sb.ToString()
}
New-Ulid
请尝试在 PowerShell 中运行这段代码,它将生成一个符合 ULID 规范的 48 位长度的 Windows ULID 字符串。
标签:buffer,bitsLeft,生成,ULID,排序,标识符 From: https://www.cnblogs.com/suv789/p/18051332