正規表現を使用してテキストのブロックでUUIDを検索しています。現在、私はすべてのUUIDが8-4-4-4-12の16進数のパターンに従うとの仮定に依存しています。
この仮定が無効であり、一部のUUIDを見逃す原因となるユースケースを誰かが考えることができますか?
正規表現を使用してテキストのブロックでUUIDを検索しています。現在、私はすべてのUUIDが8-4-4-4-12の16進数のパターンに従うとの仮定に依存しています。
この仮定が無効であり、一部のUUIDを見逃す原因となるユースケースを誰かが考えることができますか?
回答:
定義により、正規表現はUUIDを見逃さないことに同意します。ただし、特にMicrosoftのグローバル一意識別子(GUID)を検索する場合、GUIDには5つの同等の文字列表現があることに注意してください。
"ca761232ed4211cebacd00aa0057b223"
"CA761232-ED42-11CE-BACD-00AA0057B223"
"{CA761232-ED42-11CE-BACD-00AA0057B223}"
"(CA761232-ED42-11CE-BACD-00AA0057B223)"
"{0xCA761232, 0xED42, 0x11CE, {0xBA, 0xCD, 0x00, 0xAA, 0x00, 0x57, 0xB2, 0x23}}"
uuidの正規表現は次のとおりです。
\b[0-9a-f]{8}\b-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{4}-\b[0-9a-f]{12}\b
[a-f0-9]
!ヘックスなので!正規表現は(そのまま)、誤検知を返す可能性があります。
@ivelin:UUIDには大文字を使用できます。したがって、文字列をtoLowerCase()するか、次のいずれかを使用する必要があります。
[a-fA-F0-9]{8}-[a-fA-F0-9]{4}-[a-fA-F0-9]{4}-[a-fA-F0-9]{4}-[a-fA-F0-9]{12}
これにコメントしただけで十分な担当者ではなかったでしょう:)
/.../i
バージョンはしませんでした。
バージョン4のUUIDの形式はxxxxxxxx-xxxx-4xxx-yxxx-xxxxxxxxxxxxで、xは任意の16進数で、yは8、9、A、またはBのいずれかです。例:f47ac10b-58cc-4372-a567-0e02b2c3d479。
ソース:http : //en.wikipedia.org/wiki/Uuid#Definition
したがって、これは技術的にはより正確です。
/[a-f0-9]{8}-[a-f0-9]{4}-4[a-f0-9]{3}-[89aAbB][a-f0-9]{3}-[a-f0-9]{12}/
(:?8|9|A|B)
、おそらく次のように少し読みやすくなります[89aAbB]
i
(大文字と小文字を区別しない)フラグを使用します。
特定のUUIDバージョンを確認または検証する場合は、対応する正規表現を以下に示します。
なお、唯一の違いは、バージョン番号に説明され、
4.1.3. Version
の章UUID 4122 RFCは。
バージョン番号は、3番目のグループの最初の文字です[VERSION_NUMBER][0-9A-F]{3}
::
UUID v1:
/^[0-9A-F]{8}-[0-9A-F]{4}-[1][0-9A-F]{3}-[89AB][0-9A-F]{3}-[0-9A-F]{12}$/i
UUID v2:
/^[0-9A-F]{8}-[0-9A-F]{4}-[2][0-9A-F]{3}-[89AB][0-9A-F]{3}-[0-9A-F]{12}$/i
UUID v3:
/^[0-9A-F]{8}-[0-9A-F]{4}-[3][0-9A-F]{3}-[89AB][0-9A-F]{3}-[0-9A-F]{12}$/i
UUID v4:
/^[0-9A-F]{8}-[0-9A-F]{4}-[4][0-9A-F]{3}-[89AB][0-9A-F]{3}-[0-9A-F]{12}$/i
UUID v5:
/^[0-9A-F]{8}-[0-9A-F]{4}-[5][0-9A-F]{3}-[89AB][0-9A-F]{3}-[0-9A-F]{12}$/i
a-f
、各A-F
スコープの隣にも含める必要があります。
i
ケース・小文字を区別しないように正規表現マークそれの終わりに。
format
、正規表現を使用してUUIDをテストする代わりに、修飾子を「uuid」に設定して修飾子を使用する必要があります。swagger.io
/^[0-9a-f]{8}-[0-9a-f]{4}-[1-5][0-9a-f]{3}-[89AB][0-9a-f]{3}-[0-9a-f]{12}$/i
Gajusの正規表現は、有効であってもUUID V1-3および5を拒否します。
[\w]{8}(-[\w]{4}){3}-[\w]{12}
ほとんどの場合私のために働いています。
または、本当に具体的にしたい場合[\w]{8}-[\w]{4}-[\w]{4}-[\w]{4}-[\w]{12}
。
\w
は通常「単語の文字」を意味します。16進数よりもはるかに多く一致します。あなたのソリューションははるかに優れています。または、互換性/読みやすさのために使用できます[a-f0-9]
import re def valid_uuid(uuid): regex = re.compile('[\w]{8}-[\w]{4}-[\w]{4}-[\w]{4}-[\w]{12}', re.I) match = regex.match(uuid) return bool(match) valid_uuid('2wtu37k5-q174-4418-2cu2-276e4j82sv19')
python reでは、数字から大文字までのアルファベットを使用できます。そう..
import re
test = "01234ABCDEFGHIJKabcdefghijk01234abcdefghijkABCDEFGHIJK"
re.compile(r'[0-f]+').findall(test) # Bad: matches all uppercase alpha chars
## ['01234ABCDEFGHIJKabcdef', '01234abcdef', 'ABCDEFGHIJK']
re.compile(r'[0-F]+').findall(test) # Partial: does not match lowercase hex chars
## ['01234ABCDEF', '01234', 'ABCDEF']
re.compile(r'[0-F]+', re.I).findall(test) # Good
## ['01234ABCDEF', 'abcdef', '01234abcdef', 'ABCDEF']
re.compile(r'[0-f]+', re.I).findall(test) # Good
## ['01234ABCDEF', 'abcdef', '01234abcdef', 'ABCDEF']
re.compile(r'[0-Fa-f]+').findall(test) # Good (with uppercase-only magic)
## ['01234ABCDEF', 'abcdef', '01234abcdef', 'ABCDEF']
re.compile(r'[0-9a-fA-F]+').findall(test) # Good (with no magic)
## ['01234ABCDEF', 'abcdef', '01234abcdef', 'ABCDEF']
それが最も単純なPython UUID正規表現になります:
re_uuid = re.compile("[0-F]{8}-([0-F]{4}-){3}[0-F]{12}", re.I)
これらのパフォーマンスを比較するためにtimeitを使用することは、読者への課題として残しておきます。
楽しい。Pythonic™にしてください!
注:これらのスパンも一致する:;<=>?@'
ため、誤検知の可能性があると思われる場合は、近道をしないでください。(コメントでそれを指摘してくれたOliver Aubertに感謝します。)
定義により、UUIDは32桁の16進数で、5つのグループにハイフンで区切られています。正規表現を見逃してはいけません。
だから、私はリチャード・ブロノスキーが実際にこれまでのところ最高の答えを持っていると思いますが、それを少し単純にする(または少なくとももっと簡潔にする)ために少しすることができると思います:
re_uuid = re.compile(r'[0-9a-f]{8}(?:-[0-9a-f]{4}){3}-[0-9a-f]{12}', re.I)
re_uuid = re.compile(r'[0-9a-f]{8}(?:-[0-9a-f]{4}){4}[0-9a-f]{8}', re.I)
C ++のバリアント:
#include <regex> // Required include
...
// Source string
std::wstring srcStr = L"String with GIUD: {4d36e96e-e325-11ce-bfc1-08002be10318} any text";
// Regex and match
std::wsmatch match;
std::wregex rx(L"(\\{[A-F0-9]{8}-[A-F0-9]{4}-[A-F0-9]{4}-[A-F0-9]{4}-[A-F0-9]{12}\\})", std::regex_constants::icase);
// Search
std::regex_search(srcStr, match, rx);
// Result
std::wstring strGUID = match[1];