我想知道是否有办法生成有效的GUID / UUID,其中第一个(或任何部分)部分是用户选择的前缀。
即,GUID的格式为AAAAAAAA-BBBB-CCCC-DDDD-DDDDDDDDDDD,我想将任何部分设置为预定义值(理想情况下为AAA)。目标是使GUID仍然是全局唯一的,但它们不需要加密安全。
答案 0 :(得分:5)
嗯......所以,你基本上喜欢12字节的GUID?因为,一旦你删除前4个字节(你的AAA)的唯一性,你就broken the existing algorithm - 你需要提出自己的算法。
根据相关的RFC,GUID格式分解为:
UUID = time-low "-" time-mid "-"
time-high-and-version "-"
clock-seq-and-reserved
clock-seq-low "-" node
time-low = 4hexOctet
time-mid = 2hexOctet
time-high-and-version = 2hexOctet
clock-seq-and-reserved = hexOctet
clock-seq-low = hexOctet
node = 6hexOctet
hexOctet = hexDigit hexDigit
hexDigit =
"0" / "1" / "2" / "3" / "4" / "5" / "6" / "7" / "8" / "9" /
"a" / "b" / "c" / "d" / "e" / "f" /
"A" / "B" / "C" / "D" / "E" / "F"
其中唯一的静态数据是版本(4位)和保留/变量(2-3位)。我没有看到他们允许任何“用户指定”版本,但是如果您使用1111作为您的版本标识符,我会说在可预见的将来您将是安全的。现有版本在4.1.3节中,但到目前为止只定义了5个版本......在碰撞之前会再给你11个版本。
所以,如果你可以使用6或7位的清晰度,Guid.NewGuid().ToByteArray()的组合以及在你的位摆弄之后创建一个new Guid可以让你到达那里。
答案 1 :(得分:4)
抱歉,你想要一个GUID太多了。从您的问题和您自己的答案/更新中总结出来,您希望它
这是不可能的,证明: 如果可能,我可以生成一个GUID G1,你可以生成另一个GUID G2。由于我们都忽略了标准并使用相同的保留前缀,并且我对其他位的个人方案不在您的控制之内,因此我的GUID G1可能与您的GUID G2冲突。 GUID的非冲突属性遵循GUID标准。
防止冲突的机制确实具有隐私敏感性。如果我随机生成GUID G1,我可以保证如果满足两个条件,则随机GUID是唯一的:
对于您控制的子集之外的GUID,您无法保证(2)。但是,如何将GUID的非重叠子集分配给单个人?使用NIC的MAC是一种简单有效的方法。其他手段也是可能的。但无论如何,仅存在这样一个子集就是隐私隐含的。它必须属于某人,我必须能够确定这是我还是其他人。要证明两个随机GUID G1和G2是否属于同一个子集(即人)有点困难,但是当前的方案(你反对)不会试图隐藏它。
答案 2 :(得分:2)
无法创建GUID / UUID,其中第一个(或任何部分)部分是用户选择的前缀,而您可以编写自己的函数来创建具有相同数字(36/38)字符的唯一ID。
答案 3 :(得分:0)
你可以简单地创建一个Guid,并将前缀改为你想要的样子。 在操作系统项目中已经看到了这一点,通过生成如此多的guid来抛出并解决相同的问题,直到一个匹配希望的前缀(呃!)。
Guid g = Guid.NewGuid();
string gs = g.ToString();
Guid f = new Guid(string.Format("{0}-{1}", "AAAAAAAA", gs.Substring(gs.IndexOf('-') + 1)));
不好,但有效。
在这个主题的其他帖子中让我感到困扰的是,一个guid应该是全球唯一的,在所有情况下都是错误的,它有足够的空间来生成独特的guid,但没有任何保证全球唯一的。即使在制作指南时也不考虑时间。
答案 4 :(得分:0)
感谢。这些尝试的问题在于它们不能保证全局唯一,正如Raymond Chen指出的那样。我想知道是否有另一种算法生成唯一的GUID。我记得曾经有过使用时间戳和/或NIC MAC地址的实现,但它们不再使用,因为它们不具有加密性和/或存在隐私问题。
我想知道:如果我只是自己做,我应该没事?根据{{3}}:
数据4中第二个字节的一到三个最高有效位定义了GUID的类型变体:
模式描述
0网络计算系统向后兼容性
10标准
110 Microsoft组件对象模型向后兼容;这包括用于IUnknown和IDispatch等重要接口的GUID 111保留供将来使用。Data3的最重要的四位定义了版本号和使用的算法。
因此,如果我在Data3 / Data4中构建一些东西,我通常会创建自己的实现,不应该与任何其他GUID冲突,但当然总是存在一些与之相关的风险,所以在此之前我想要检查是否有更老的/不再使用的algorhithm产生真正的唯一ID。
答案 5 :(得分:0)
我最近有类似的需求 - 我需要一个GUID:
正如您可能想象的那样,我正在做一些我不应该做的事情。
你在其中一条评论中提到你可以让GUID生成器运行,直到碰巧用你需要的前缀命中guid。这就是我采取的策略。这是代码:
using System;
namespace ConsoleApplication1
{
class Program
{
static void Main(string[] args)
{
string target_prefix = "dead";
while (true)
{
Guid g = Guid.NewGuid();
string gs = g.ToString();
if (gs.Substring(0, target_prefix.Length) == target_prefix)
{
Console.WriteLine("Match: " + gs);
}
else
{
//Console.WriteLine("Mismatch: " + gs);
}
}
}
}
}
对于较小的前缀,它可以更快地生成匹配。我敢打赌它是目标前缀每个数字的16倍。