Вопрос

Можно ли сгенерировать короткий GUID, как на YouTube (N7Et6c9nL9w)?

Как это можно сделать?Я хочу использовать его в веб-приложении.

Это было полезно?

Решение

Вы можете использовать Base64:

string base64Guid = Convert.ToBase64String(Guid.NewGuid().ToByteArray());

Это генерирует строку типа E1HKfn68Pkms5zsZsvKONw==.Поскольку GUID всегда имеет длину 128 бит, вы можете опустить == который, как вы знаете, всегда будет присутствовать в конце и даст вам строку из 22 символов.Однако он не такой короткий, как YouTube.

Другие советы

9 символов — это не руководство.Учитывая это, вы можете использовать шестнадцатеричное представление целого числа, что дает вам строку из 8 символов.

Обновление 1: Не знаю, почему вышеизложенное получило отрицательный голос, но для тех, кому интересно:

Вы можете использовать идентификатор, который у вас уже есть.Также вы можете использовать .GetHashCode для разных простых типов, и тогда у вас будет другой int.Вы также можете выполнить xor различных полей.И если вам это нравится, вы можете даже использовать случайное число - эй, у вас есть намного больше 2 000 000 000+ возможных значений, если вы придерживаетесь положительных сторон;)

Как уже упоминалось в принятом ответе, могут возникнуть проблемы, если вы используете GUID в URL-адресе.Вот более полный ответ:

    public string ToShortString(Guid guid)
    {
        var base64Guid = Convert.ToBase64String(guid.ToByteArray());

        // Replace URL unfriendly characters with better ones
        base64Guid = base64Guid.Replace('+', '-').Replace('/', '_');

        // Remove the trailing ==
        return base64Guid.Substring(0, base64Guid.Length - 2);
    }

    public Guid FromShortString(string str)
    {
        str = str.Replace('_', '/').Replace('-', '+');
        var byteArray = Convert.FromBase64String(str + "==");
        return new Guid(byteArray);
    }

Использование:

        var guid = Guid.NewGuid();
        var shortStr = ToShortString(guid);
        // shortStr will look something like 2LP8GcHr-EC4D__QTizUWw
        var guid2 = FromShortString(shortStr);
        Assert.AreEqual(guid, guid2);

Как уже упоминалось, YouTube VideoId технически не является GUID, поскольку он не уникален по своей сути.

Согласно Википедия:

Общее количество уникальных ключей — 2.128 или 3,4×1038.Это число настолько велик, что вероятность того же числа генерируется случайным образом дважды, незначительна.

Уникальность YouTube VideoId поддерживается их алгоритмом генератора.

Вы можете либо написать свой собственный алгоритм, либо использовать какой-нибудь генератор случайных строк и использовать UNIQUE CONSTRAINT ограничение в SQL для обеспечения его уникальности.

Сначала создайте UNIQUE CONSTRAINT в вашей базе данных:

ALTER TABLE MyTable
ADD CONSTRAINT UniqueUrlId
UNIQUE (UrlId);

Затем, например, сгенерируйте случайную строку (из файла philipproplesch отвечать):

string shortUrl = System.Web.Security.Membership.GeneratePassword(11, 0);

Если сгенерированный UrlId является достаточно случайным и достаточно длинным, вы редко должны сталкиваться с исключением, которое выдается, когда SQL обнаруживает дубликат. UrlId.В таком случае вы можете легко обработать исключение в своем веб-приложении.

Технически это не Гайд.На Youtube есть простой генератор рандомизированных строк, который вы, вероятно, сможете создать за несколько минут, используя массив разрешенных символов и генератор случайных чисел.

Возможно, это не лучшее решение, но вы можете сделать что-то вроде этого:

string shortUrl = System.Web.Security.Membership.GeneratePassword(11, 0);

Вероятно, этот идентификатор не является глобально уникальным.GUID должны быть глобально уникальными, поскольку они включают элементы, которые не должны встречаться где-либо еще (MAC-адрес машины, генерирующей идентификатор, время создания идентификатора и т. д.).

Если вам нужен уникальный идентификатор в вашем приложении, используйте числовой фонтан, возможно, закодировав значение как шестнадцатеричное число.Каждый раз, когда вам понадобится идентификатор, берите его из фонтанчика номеров.

Если у вас есть несколько серверов, распределяющих идентификаторы, вы можете получить диапазон чисел (несколько десятков или тысяч, в зависимости от того, как быстро вы распределяете идентификаторы), и это должно сработать.8-значное шестнадцатеричное число даст вам 4 миллиарда идентификаторов, но ваш первый идентификатор будет намного короче.

Это не GUID

Позвольте мне перейти к следующему

Он использует TotalMilliseconds от EPOCH и допустимый набор символов.

Это не будет глобально уникальным, но уникальным для экземпляра, в котором оно определено.

public string YoutubeLikeId()
{
    Thread.Sleep(1);//make everything unique while looping
    long ticks = (long)(DateTime.UtcNow.Subtract(new DateTime(1970, 1, 1,0,0,0,0))).TotalMilliseconds;//EPOCH
    char[] baseChars = new char[] { '0','1','2','3','4','5','6','7','8','9',
            'A','B','C','D','E','F','G','H','I','J','K','L','M','N','O','P','Q','R','S','T','U','V','W','X','Y','Z',
            'a','b','c','d','e','f','g','h','i','j','k','l','m','n','o','p','q','r','s','t','u','v','w','x'};

    int i = 32;
    char[] buffer = new char[i];
    int targetBase= baseChars.Length;

    do
    {
        buffer[--i] = baseChars[ticks % targetBase];
        ticks = ticks / targetBase;
    }
    while (ticks > 0);

    char[] result = new char[32 - i];
    Array.Copy(buffer, i, result, 0, 32 - i);

    return new string(result);
}

На выходе будет что-то вроде

XOTgBsu
XOTgBtB
XOTgBtR
XOTgBtg
XOTgBtw
XOTgBuE

Обновлять: Того же самого можно добиться от Guid как

var guid = Guid.NewGuid(); 
guid.ToString("N");
guid.ToString("N").Substring(0,8);
guid.ToString("N").Substring(8,4);
guid.ToString("N").Substring(12,4);
guid.ToString("N").Substring(16,4);
guid.ToString("N").Substring(20,12);

Для гида ecd65132-ab5a-4587-87b8-b875e2fe0f35 он разобьет его на куски, так как ecd65132 ,ab5a , 4587,87b8,b875e2fe0f35

но я не могу гарантировать, что он всегда будет уникальным.

Обновление 2: Еще есть проект под названием Короткое руководство чтобы получить дружественный URL GUID его можно конвертировать из/в обычный Guid

Лицензировано под: CC-BY-SA с атрибуция
Не связан с StackOverflow
scroll top