У меня есть функция PHP для создания этих известных AlphaID представлений целых чисел следующим образом:
function alphaID( $input ) {
$index = 'abcdefghijklmnopqrstuvwxyz0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZ';
$base = strlen( $index );
$input += pow( $base, 4 );
$output = '';
for( $i = floor( log( $input, $base ) ); $i >= 0; $i-- ) {
$bcp = bcpow( $base, $i );
$start = floor( $input / $bcp ) % $base;
$output .= substr( $index, $start, 1 );
$input = $input - ( $start * $bcp );
}
return $output;
}
Кодирование, например, максимального целого числа, предоставленного PHP_MAX_INT константа (2147483647) вернется cwuCBb
Но я думал, что это было слишком медленно во всей картине приложения, поэтому я попытался создать функцию MYSQL, поэтому, теоретически, я бы не стал терять производительность, выполняя такое преобразование с помощью PHP, когда данные будут готовы для меня во время запросов.
Руководство по MySQL не совсем дружелюбно, но, ища кое-где, я пришел к следующему:
DROP FUNCTION IF EXISTS ENCODE_ALPHAID;
DELIMITER $$
CREATE FUNCTION ENCODE_ALPHAID( input integer ) RETURNS CHAR( 6 ) DETERMINISTIC
BEGIN
DECLARE output CHAR( 6 );
DECLARE letters CHAR( 62 );
DECLARE base TINYINT( 2 );
DECLARE iterator TINYINT( 2 );
DECLARE bcp CHAR( 9 );
DECLARE start TINYINT( 2 );
SET output = '';
SET letters = 'abcdefghijklmnopqrstuvwxyz0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZ';
SET base = CHAR_LENGTH( letters );
SET input = input + POW( base, 4 );
SET iterator = FLOOR( LOG( base, input ) );
ENCODING: LOOP
SET bcp = POW( base, iterator );
SET start = FLOOR( input / bcp ) % base + 1;
SET output = CONCAT( output, SUBSTR( letters, start, 1 ) );
SET input = input - ( start * bcp );
SET iterator = iterator-1;
IF iterator < 0 THEN LEAVE ENCODING; END IF;
END LOOP ENCODING;
RETURN output;
END $$
DELIMITER ;
Но когда я запустил его через менеджер MySQL, я использую (DBNinja), видимо, ничего не происходит. После запуска запроса он показывает Затронут 0 ряд и я не уверен, является ли это ожидаемым результатом или нет.
Правильно или нет, функция не работала в любом случае, потому что, когда я пытался использовать ее в запросе:
SELECT ENCODE_ALPHAID( `c`.`cid` ) from `table` c WHERE `c.user` = 1
Я впервые получил сообщение об ошибке table.ENCODE_ALPHAID не существовало Затем я заметил, что, действительно, я создал эту функцию, находясь в другой базе данных, которую я пытался использовать.
Но я создал его снова, в соответствующей базе данных, но появилась та же ошибка.
Итак, вот вопросы:
обновленный
Очевидно, что проблема с не создаваемой функцией находится на конце DBNinja, потому что я выполнил оператор непосредственно в консоли MySQL и, хотя с тем же статусом вывода Затронуто 0 строк, Я смог эффективно использовать функцию в выражении, поэтому функция была создана в конце концов.
Тем не менее, что-то не так с самой подпрограммой, потому что, когда я тестировал ее, полученная строка была … «впереди».
Например, если я запускаю следующий код PHP:
echo alphaID( 2 );
Было бы производить baaac, но функция MySQL возвращается baaad, который будет AlphaID представление целого числа 3
Мало того, что это неправильно, но я думаю, что это может также переполнить тип INT, используемый при достижении максимума 2147483647
Бруно,
из версии MySQL вам не хватает:
Условие окончания цикла должно быть:
ЕСЛИ итератор < 0 ТО
Оставьте кодирование;
END IF;
При использовании CONCAT убедитесь, что вы не используете CONCAT NULL (вам следует инициализировать параметры)
Рутины всегда создаются в одной базе данных. Вы можете вызвать их в любом из них (если у вас есть права), включив имя базы данных в запрос:
call mydb.ENCODE_ALPHAID( 2147483647 );
Кроме того, при объявлении переменных вы можете использовать префиксы, чтобы переменные не смешивались с возможными именами столбцов / зарезервированными словами. Например, вместо «output» используйте «v_output».
Похоже, вы пропустили END IF; Не используйте зарезервированные слова для переменных. Если вы хотите пойти по злому пути, обязательно процитируйте их .ie `table«,. Обратите внимание на обратную галочку — не одиночные кавычки. На моей машине этот код возвращает ноль:
CREATE DEFINER=`root`@`localhost` FUNCTION `ENCODE_ALPHAID`(`input` INT)
RETURNS CHAR(6) DETERMINISTIC NO SQL SQL SECURITY DEFINER
BEGIN
DECLARE output CHAR(6);
DECLARE `index` CHAR(62);
DECLARE base TINYINT(2);
DECLARE iterator TINYINT( 2 );
DECLARE bcp CHAR( 9 );
DECLARE start TINYINT( 2 ); SET `index` = 'abcdefghijklmnopqrstuvwxyz0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZ';
SET base = CHAR_LENGTH( `index` );
SET iterator = FLOOR( LOG( base, input ) );
ENCODING: LOOP
SET bcp = POW( base, iterator );
SET start = FLOOR( input / bcp ) % base;
SET output = CONCAT( output, SUBSTR( `index`, start, 1 ) );
SET input = input - ( start * bcp );
SET iterator = iterator-1;
IF iterator >= 0 THEN LEAVE ENCODING;
END IF;
END LOOP ENCODING;
RETURN output;
END;
PS: на спине отметьте галочкой один. Я понятия не имею, как избежать уценки. А также eaid
это более короткое имя, которое я использовал