Warning: file_get_contents(/data/phpspider/zhask/data//catemap/8/sorting/2.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
PostgreSQL中的字母数字排序_Postgresql_Sorting_Natural Sort_Bytea - Fatal编程技术网

PostgreSQL中的字母数字排序

PostgreSQL中的字母数字排序,postgresql,sorting,natural-sort,bytea,Postgresql,Sorting,Natural Sort,Bytea,我在Postgres 9.6中有一个带有字符变化的列的表: id | column ------------ 1 |IR ABC-1 2 |IR ABC-2 3 |IR ABC-10 我看到一些解决方案将列类型转换为bytea select * from table order by column::bytea. 但它总是导致: id | column ------------ 1 |IR ABC-1 2 |IR ABC-10 3 |IR ABC-2 我不知道为什么“10”

我在Postgres 9.6中有一个带有字符变化的
列的表:

id | column 
------------
1  |IR ABC-1
2  |IR ABC-2
3  |IR ABC-10
我看到一些解决方案将列类型转换为
bytea

select * from table order by column::bytea.
但它总是导致:

id | column 
------------
1  |IR ABC-1
2  |IR ABC-10
3  |IR ABC-2

我不知道为什么“10”总是在“2”之前。假设排序的基础是字符串的最后一个整数,而不管该数字之前的字符是什么,我如何对该表进行排序。

如注释中所示,拆分并转换整数部分

select *
from
    table
    cross join lateral
    regexp_split_to_array(column, '-') r (a)
order by a[1], a[2]::integer

在对字符数据类型进行排序时,应用-除非您使用区域设置“C”,它按字节值对字符进行排序。应用排序规则可能是可取的,也可能是不可取的。在任何情况下,这都会使分拣变得更加昂贵。如果要在没有排序规则的情况下进行排序,请不要强制转换为
bytea
,而是使用
COLLATE“C”

SELECT * FROM table ORDER BY column COLLATE "C";
然而,这并不能解决您提到的字符串中的数字问题。拆分字符串并将数字部分按数字排序

SELECT *
FROM   table
ORDER  BY split_part(column, '-', 2)::numeric;
或者,如果您的所有数字都适合
bigint
甚至
integer
,请改用它(更便宜)

我忽略了主要部分,因为你写道:

。。。排序的基础是字符串的最后一个整数,而不管该数字之前的字符是什么

相关的:

通常,最好将字符串的不同部分保存在单独的列中,作为相应的数据类型,以避免任何此类混淆


如果引线串对于所有列是相同的,考虑只删除冗余噪声。您始终可以使用a来预先编写字符串以供显示,或者以便宜的方式动态执行。

10
位于
2
之前,因为
1
位于
2
之前。请查看现有的问题。如果您想按名称排序,然后按编号细分,则必须将这两个实体分为两列,然后按两列顺序排列。@evert,我想我能把你的想法带到某个地方。。但是如何拆分列字符串呢?如果
column
始终采用您在示例中给出的格式,您只需执行
split_part(column'-',2)::integer
即可从中获取整数。否则,regexp可能会更好。