Почему функция PHPs uniqid возвращает только 13 цифр, а не 14?


uniqid() функция возвращает шестнадцатеричное число длиной 13 цифр. Согласно спецификации в php.net site , функция использует microtime для генерации уникального значения.

Но microtime возвращает числа в строковом формате следующим образом:

"0.70352700 12689396875"

Которые в основном являются микросекундами и секундами, прошедшими с 1970 года. Это десятичное число из 9+11 цифр.

Преобразование 20 десятичного числа в шестнадцатеричное привело бы к 16-значному шестнадцатеричному числу, а не к 13-значному один.

Я также думал убрать "0."часть, которая, кажется, никогда не меняется, и последние две цифры части микросекунды, которые, кажется, остаются всегда "00". При этом десятичное число будет иметь длину всего 9+11-3 цифр, но все же десятичное число из 17 цифр при преобразовании в шестнадцатеричное приведет к 14-значному шестнадцатеричному числу, а не 13.

Я НЕ ЗАИНТЕРЕСОВАН В ПОЛУЧЕНИИ УНИКАЛЬНОГО ИДЕНТИФИКАТОРА ДРУГИМ СПОСОБОМ ИЛИ БОЛЕЕ ДЛИННОГО / КОРОТКОГО УНИКАЛЬНОГО ИДЕНТИФИКАТОРА! Я ТОЛЬКО СПРАШИВАЮ, ЗНАЕТ ЛИ КТО-НИБУДЬ ПОЧЕМУ. Uniqid возвращает только 13 цифр.

Кажется nosense: если uniqid возвращает на одну цифру меньше, чем microtime, это означает, что microtime выдает результаты, которые являются более уникальными из возвращаемых uniqid.

4 9

4 ответа:

Нашел это на http://www.php.net/manual/en/function.uniqid.php#95001

Имеет смысл для меня. Комментарий, если вам нужно объяснение

Для записи, лежащая в основе функция для uniqid () выглядит следующим образом примерно так:

$m=microtime (true); функции sprintf("%8х%05x\Н",этаж (млн$), ($м этаже($м))*1000000);

Другими словами, первые 8 шестнадцатеричных символов = Unixtime, последние 5 шестнадцатеричных символов = микросекунды. Вот почему он имеет микросекундная точность. Кроме того, это обеспечивает средство, с помощью которого реверс-инженер время, когда uniqid был сгенерирован:

Дата("r", hexdec (substr (uniqid(),0,8)));

Все больше по мере того, как вы идете дальше вниз строка, число становится "больше уникальный " с течением времени, за исключением цифры 9, где числовое преобладание равно 0..3>4>5..f, из-за разница между 10^6 и 16^5 (это предположительно верно для остальных цифры тоже но гораздо меньше заметный).

Я думаю, что число, порожденное uniqid это основано на текущем времени в микросекундах-но это не то время : расчет, вероятно, немного сложнее, чем вы думаете.

Тем не менее, если вам нужно больше 13 цифр, вы можете передать true в качестве второго параметра в uniqid, чтобы иметь больше энтропии-и это даст вам строку длиной 23 символа.


Например, с этой частью кода:

var_dump(uniqid());
var_dump(uniqid('', true));

Я только что получил:

string '4ba284384e4ca' (length=13)
string '4ba284384e4df9.73439132' (length=23)

Для 32-символьного уникального идентификатора попробуйте сделать следующее:

$unique = uniqid(rand(), true);

Чтобы сократить его, просто используйте substr ():

$unique = substr(uniqid(rand(), true), 16, 16); // 16 characters long

В руководстве по PHP значение по умолчанию равно 13, а значение $more_entropy равно true, но вы всегда будете иметь метку времени Unix.

Я часто использую $uid = md5( uniqid() );

Обновление:
Теперь это даст вам 32 символа с минимальным шансом столкновения именно в этой жизни.

md5(uniqid(mt_rand(), true));