2013-06-02 82 views
1

我一直在閱讀UUID RFC http://www.ietf.org/rfc/rfc4122.txt和使用python uuid模塊進行實驗。爲了便於解釋,這裏是從規範中解除的UUID圖。什麼是最小和最大的有效第一類UUID?

0     1     2     3 
    0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5 6 7 8 9 0 1 
    +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ 
    |       time_low        | 
    +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ 
    |  time_mid    |   time_hi_and_version | 
    +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ 
    |clk_seq_hi_res | clk_seq_low |   node (0-1)   | 
    +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ 
    |       node (2-5)       | 
    +-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+-+ 
按照我對規範的讀

,最小的1型UUID應該有time_low,time_mid,clk_seq_hi_res,clk_seq_low和節點設置爲全0,和time_hi_and_version應該有15位設置爲1,最大類型1的UUID應該有time_low,time_mid,clk_seq_hi_res,clk_seq_low和節點設置爲全1,並且time_hi_and_version設置爲全1,除了位12,13和14.

但是,試圖在python中生成這些失敗:

>>> u = uuid.UUID("{00000000-0000-0000-0001-00000000}") 
Traceback (most recent call last): 
    File "<stdin>", line 1, in <module> 
    File "/usr/local/Cellar/python/2.7.4/Frameworks/Python.framework/Versions/2.7/lib/python2.7/uuid.py", line 134, in __init__ 
    raise ValueError('badly formed hexadecimal UUID string') 
ValueError: badly formed hexadecimal UUID string 

>>> u = uuid.UUID("{ffffffff-ffff-ffff-fff1-ffffffff}")                                       
Traceback (most recent call last): 
    File "<stdin>", line 1, in <module> 
    File "/usr/local/Cellar/python/2.7.4/Frameworks/Python.framework/Versions/2.7/lib/python2.7/uuid.py", line 134, in __init__ 
    raise ValueError('badly formed hexadecimal UUID string') 
ValueError: badly formed hexadecimal UUID string 

我假定我我錯誤地閱讀了這個規範,但我很茫然。

回答

1

問題不在於您的特定值,而在於您沒有足夠的值。

您只提供了14個字節的數據而不是16個,這就是它的抱怨。

UUID根本沒有檢查類型1 UUID的要求。如果是這樣,它將無法爲其他UUID類型工作,這些UUID類型具有不同的要求。

試試這個:

In [58]: uuid.UUID("{00000000-0000-0000-0000-000000000000}") 
Out[58]: UUID('00000000-0000-0000-0000-000000000000') 
In [59]: uuid.UUID('{FFFFFFFF-FFFF-FFFF-FFFF-FFFFFFFFFFFF}') 
Out[59]: UUID('ffffffff-ffff-ffff-ffff-ffffffffffff') 

同時,你也顯然混淆的版本和變異,並有你的字節順序落後。所以讓我們從頭開始。

根據我的規格,最小的1型UUID的閱讀... 應該有time_low,time_mid,clk_seq_hi_res,clk_seq_low和節點設置爲全0

clk_seq_hi_resclock_sequence_hi_and_reserved的縮寫,在4.1.2節中定義爲「與變體複用的時鐘序列的高場」。該變體在4.1.1中定義,並且您希望「本文檔中指定的變體」分別將兩個最高有效位分別設置爲1和0。因此,這個字段不能全爲0,也不能全爲1。由於這是有效位,而非最低位,這意味着八位位組8的高位半字節必須是(8, 9, a, b)之一,而不是低位半字節必須是(1, 5, 9, d)之一。

,和time_hi_and_version應具有第15位設置爲1。

否,版本號被作爲4.1.3時間戳的最顯著4位所描述的,和版本1被定義爲0-0-0-1。因此,第15位應該設置爲0,14和13以及第12位應該設置爲1.這意味着第8個字節的整個最高半字節必須是1,而不是第8個字節的低半字節。

所以:

00000000-0000-1000-8000-000000000000 
ffffffff-ffff-1fff-bfff-ffffffffffff 

注意,這些時間戳表示的日期是有點傻。前者是1582年10月15日的午夜,後者是在53世紀。*因此,任何確認版本-1 UUID的庫都可能會拒絕它們。

此外,全0的節點是全0的全球單播MAC地址,我不確定這是一個有效的IEEE-802地址。所有1的節點都很好,因爲如果設置了多播位,則明確允許使用隨機數。


*各種BBCdocumentariesassociated textbooks解釋,由第49世紀,人類將有時間旅行,這將迫使我們改變我們所有的時間戳技術。

+0

啊優點:)它看起來像python uuid在施工時不會對數據進行任何驗證,但是您可以使用'version'屬性檢查一些後置條件,例如。但是,我的原始問題仍然存在。什麼是最小和最大的_valid_ type-1 UUID? –

+0

嗯,它_does_做驗證 - 它驗證你的數據形成一個有效的UUID結構。但它不會將其驗證爲第1類UUID,因爲它會拒絕有效的第2類至第5類UUID。但至於你的其他問題,讓我更新答案。 – abarnert

相關問題