使用rpad在Postgresql中填充字符串而不截断它

dmo*_*ius 7 sql string postgresql function string-formatting

使用Postgresql 8.4,如何在没有截断字符串的情况下用空格对字符串进行右键填充?

问题是当字符串实际上长于要填充的字符数时rpad 截断字符串.例:

SELECT rpad('foo', 5);  ==> 'foo  ' -- fine
SELECT rpad('foo', 2);  ==> 'fo'    -- not good, I want 'foo' instead.
Run Code Online (Sandbox Code Playgroud)

我找到的最短解决方案根本不涉及rpad:

SELECT 'foo' || repeat(' ', 5-length('foo'));  ==> 'foo  ' -- fine
SELECT 'foo' || repeat(' ', 2-length('foo'));  ==> 'foo'   -- fine, too
Run Code Online (Sandbox Code Playgroud)

但这看起来丑陋恕我直言.请注意,我当然不会选择字符串'foo',而是从列中选择:

SELECT colname || repeat(' ', 30-length(colname)) FROM mytable WHERE ...
Run Code Online (Sandbox Code Playgroud)

有更优雅的解决方案吗?

Tim*_*olo 8

找到了一个更优雅的解决方案:

SELECT greatest(colname,rpad(colname, 2));
Run Code Online (Sandbox Code Playgroud)

例如:

SELECT greatest('foo',rpad('foo', 5));  -- 'foo  ' 
SELECT greatest('foo',rpad('foo', 2));  -- 'foo'  
Run Code Online (Sandbox Code Playgroud)

.


解释它是如何工作的:rpad('foo',5)='foo'>>'foo'(最好用于字符串和数字)rpad('foo',2)='fo'是<' foo',所以'foo'是由最大的功能选择的.

如果你想要左边填充的单词,你不能使用最大的单词,因为它从左到右比较(例如'oo'和'foo'),在某些情况下,这将取决于字符串的大小.我想你可以反转字符串并使用rpad并将其反转,或者只使用在两种情况下都有效的原始解决方案.


mu *_*ort 7

如果您不想一直编写该repeat业务,只需编写自己的函数即可.像这样的东西:

create or replace function rpad_upto(text, int) returns text as $$
begin
    if length($1) >= $2 then
        return $1;
    end if;
    return rpad($1, $2);
end;
$$ language plpgsql;
Run Code Online (Sandbox Code Playgroud)

或这个:

create or replace function rpad_upto(text, int) returns text as $$
select $1 || repeat(' ', $2 - length($1));
$$ language sql;
Run Code Online (Sandbox Code Playgroud)

然后你可以这样说:

select rpad_upto(colname, 30) from mytable ...
Run Code Online (Sandbox Code Playgroud)

你可能想要考虑你想要rpad_upto(null, n)产生什么.rpad_upto如果$1为NULL ,则上面的两个版本都将返回NULL,但您可以调整它们以返回其他内容而没有太大困难.