PostgreSQL:是否有一个函数可以将base-10 int转换为base-36字符串?

PostgreSQL:是否有一个函数可以将base-10 int转换为base-36字符串?,postgresql,Postgresql,PostgreSQL中是否有一个函数可以将基数为10的数字(如30转换为基数为36的表示形式(如u)?有base-64函数(如),但base-36没有。但你可以自己写一本,或者: CREATE或REPLACE函数base36\u encode(以数字bigint表示,以最小宽度int=0表示)将varchar返回为$$ 声明 chars char[]; ret varchar; 瓦尔·比金; 开始 字符:=数组['0','1','2','3','4','5','6','7','8','9','A

PostgreSQL中是否有一个函数可以将基数为10的数字(如
30
转换为基数为36的表示形式(如
u
)?

有base-64函数(如),但base-36没有。但你可以自己写一本,或者:

CREATE或REPLACE函数base36\u encode(以数字bigint表示,以最小宽度int=0表示)将varchar返回为$$
声明
chars char[];
ret varchar;
瓦尔·比金;
开始
字符:=数组['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'];
val:=位数;
ret:='';
如果val<0,则
val:=val*-1;
如果结束;
而瓦尔!=0循环
ret:=字符[(val%36)+1]| | ret;
val:=val/36;
端环;
如果最小宽度>0且字符长度(ret)<最小宽度,则
ret:=lpad(ret,最小宽度,'0');
如果结束;
返回ret;
结束;
$$语言plpgsql不可变;

我认为您应该问问自己,数据库是否是处理此类数据格式的正确位置。不过,类似这样的表示问题最好在接近堆栈的最终查看级别时处理。

这是一个可以接受任何大小的数字的版本,它使用的数据类型是“数字”这是bignum的postgresql实现

CREATE OR REPLACE FUNCTION base36_encode(IN digits numeric, IN min_width int = 0) RETURNS text AS $$
DECLARE
    chars char[] := ARRAY['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' ] ;  
    ret text:=''; 
    val numeric:= digits; 
BEGIN
    IF digits < 0 THEN 
        val := -val;
    END IF; 

    WHILE val > 0 OR min_width > 0 LOOP 
        ret := chars[(mod(val,36))+1] || ret; 
        val := div(val,36); 
        min_width := min_width-1;
    END LOOP;
    IF digits < 0 THEN 
        ret := '-'||ret; 
    END IF; 
    RETURN ret;
END;
$$ LANGUAGE plpgsql IMMUTABLE;
创建或替换函数base36\u encode(数字形式,最小宽度int=0)将文本返回为$$
声明
字符字符[]:=数组['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'];
ret text:='';
val数值:=位数;
开始
如果数字小于0,则
val:=-val;
如果结束;
当val>0或min_width>0循环时
ret:=字符[(mod(val,36))+1]| | ret;
val:=div(val,36);
最小宽度:=最小宽度-1;
端环;
如果数字小于0,则
ret:='-'| | ret;
如果结束;
返回ret;
结束;
$$语言plpgsql不可变;

不幸的是,链接的博客帖子已经死了。您没有准备好这样一种算法,用于用TEA表示较长数字的
表示?:-)@卢卡塞德:我不知道你在问什么。您有一个
bytea
列,您想在数据库中编码为base-36?如果您有一个bytea,您想用一个合理的块大小来编码二进制数据,比如
base32
。base36将超过31位转换为6个字符,非常适合于有符号的
int32\t
,而对于二进制数据则不太有用。31字节=48个字符的块大小有点不合适。你是对的,虽然我很欣赏这个解决方案,但这类内容不应该作为函数编码到数据库中。你可以使用
abs
函数,所以节省几行。整数实际上是二进制的,10进制只用于与人通信。。
CREATE OR REPLACE FUNCTION base36_encode(IN digits numeric, IN min_width int = 0) RETURNS text AS $$
DECLARE
    chars char[] := ARRAY['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' ] ;  
    ret text:=''; 
    val numeric:= digits; 
BEGIN
    IF digits < 0 THEN 
        val := -val;
    END IF; 

    WHILE val > 0 OR min_width > 0 LOOP 
        ret := chars[(mod(val,36))+1] || ret; 
        val := div(val,36); 
        min_width := min_width-1;
    END LOOP;
    IF digits < 0 THEN 
        ret := '-'||ret; 
    END IF; 
    RETURN ret;
END;
$$ LANGUAGE plpgsql IMMUTABLE;