Как проверить, что значение равно UUID4, сгенерированному этим кодом?
uuid.uuid4().hex
Должно ли быть какое-то регулярное выражение? Значения, сгенерированные строками длиной 32 символа этой формы:
60e3bcbff6c1464b8aed5be0fce86052
Как проверить, что значение равно UUID4, сгенерированному этим кодом?
uuid.uuid4().hex
Должно ли быть какое-то регулярное выражение? Значения, сгенерированные строками длиной 32 символа этой формы:
60e3bcbff6c1464b8aed5be0fce86052
достаточно просто:
import re
uuid4hex = re.compile('[0-9a-f]{32}\Z', re.I)
Это соответствует только строкам, которые представляют собой ровно 32 шестнадцатеричных символа, если вы используете метод .match()
(поиск начинается с начала строки, см. .search()
против .match()
). \Z
соответствует концу строки (vs. $
, которая будет соответствовать в конце строки или новой строки).
Насколько я знаю, ответ Martijn не соответствует 100%. UUID-4 имеет пять групп шестнадцатеричных символов, первый имеет 8 символов, второй 4 символа, третий 4 символа, четвертый 4 символа, пятый 12 символов.
Однако, чтобы сделать его допустимым UUID4, третья группа (первая в средняя) должна начинаться с 4:
00000000-0000-4000-0000-000000000000
^
И четвертая группа должна начинаться с 8, 9, a или b.
00000000-0000-4000-a000-000000000000
^ ^
Итак, вам нужно изменить регулярное выражение Martijn на:
import re
uuid4hex = re.compile('[0-9a-f]{12}4[0-9a-f]{3}[89ab][0-9a-f]{15}\Z', re.I)
Надеюсь, это поможет!
Чтобы быть более конкретным. Это самое точное регулярное выражение для ловли uuid4 как с типом, так и без него, и это следует за всеми правилами UUID4:
[a-f0-9]{8}-?[a-f0-9]{4}-?4[a-f0-9]{3}-?[89ab][a-f0-9]{3}-?[a-f0-9]{12}
Вы можете убедиться, что он также набирает заглавные буквы с флагом игнорирования. В моем примере с re.I. (uuid не имеет заглавных букв в нем, но во входных данных он не прерывается, просто игнорирует его. Значение UUID "f" и "F" одинаково)
Я создал валидатор, чтобы поймать их так:
def valid_uuid(uuid):
regex = re.compile('^[a-f0-9]{8}-?[a-f0-9]{4}-?4[a-f0-9]{3}-?[89ab][a-f0-9]{3}-?[a-f0-9]{12}\Z', re.I)
match = regex.match(uuid)
return bool(match)
Затем вы можете сделать:
if valid_uuid(my_uuid):
#Do stuff with valid my_uuid
С помощью ^ в начале и \Z в конце я также удостоверяюсь, что в строке ничего нет. Это гарантирует, что "3fc3d0e9-1efb-4eef-ace6-d9d59b62fec5" возвращает true, но "3fc3d0e9-1efb-4eef-ace6-d9d59b62fec5 + 19187" возвращает false.
Обновление - ниже приведенный ниже метод python не является надежным - см. комментарии:
Существуют другие способы проверки UUID. В python выполните:
from uuid import UUID
try:
UUID(my_uuid)
#my_uuid is valid and you can use it
except ValueError:
#do what you need when my_uuid is not a uuid
В качестве справки по проблемам производительности я протестировал оба способа с точки зрения времени выполнения, а метод проверки регулярных выражений немного быстрее:
import re
from uuid import UUID
def _validate_uuid4(uuid_string):
try:
UUID(uuid_string, version=4)
except ValueError:
return False
return True
def _validate_uuid4_re(uuid_string):
uuid4hex = re.compile('^[a-f0-9]{8}-?[a-f0-9]{4}-?4[a-f0-9]{3}-?[89ab][a-f0-9]{3}-?[a-f0-9]{12}\Z', re.I)
match = uuid4hex.match(uuid_string)
return bool(match)
В команде ipython
:
В [58]: val = str (uuid.uuid4())
In [59]:% time _validate_uuid4 (val) Время ЦП: пользователь 0 нс, sys: 0 нс, всего: 0 нс Время стены: 30,3 мкс Out [59]: верно
In [60]:% time _validate_uuid4_re (val) Время ЦП: пользователь 0 нс, sys: 0 нс, всего: 0 нс Время стены: 25,3 мкс Выход [60]: верно
В [61]: val = "invalid_uuid"
В [62]:% time _validate_uuid4 (val) Время ЦП: пользователь 0 нс, sys: 0 нс, всего: 0 нс Время стены: 29,3 мкс Выход [62]: Ложь
В [63]:% time _validate_uuid4_re (val) Время ЦП: пользователь 0 нс, sys: 0 нс, всего: 0 нс Время стены: 25,5 мкс Выход [63]: Ложь