如何进行自然排序?
即按字母数字组合数据的顺序排列,如下:
Season 1, Season 2, Season 10, Season 20
而不是
Season 1, Season 10, Season 2, Season 20
我会用一个非常实用的电视季节案例来说明,这是一种非常实用的格式。
我希望实现以下目标:
- 分享我的解决方案给其他人
- 请你帮忙想办法缩短它(或找到更好的解决方案)
- 您能解决下面的第7个标准吗?
在SO和其他网站上找到的一些解决方案只适用于90%的情况。但是,如果您的文本中有多个数字值,大多数/全部都不起作用,或者如果在文本中找不到数字,则会导致SQL错误。
我创建了这个SQLFiddle链接来进行测试(包括下面的所有代码)。
这是创建语句:
create table tvseason
(
title varchar(100)
);
insert into tvseason (title)
values ('100 Season 03'), ('100 Season 1'),
('100 Season 10'), ('100 Season 2'),
('100 Season 4'), ('Show Season 1 (2008)'),
('Show Season 2 (2008)'), ('Show Season 10 (2008)'),
('Another Season 01'), ('Another Season 02'),
('Another 1st Anniversary Season 01'),
('Another 2nd Anniversary Season 01'),
('Another 10th Anniversary Season 01'),
('Some Show Another No Season Number'),
('Some Show No Season Number'),
('Show 2 Season 1'),
('Some Show With Season Number 1'),
('Some Show With Season Number 2'),
('Some Show With Season Number 10');
这是我的工作解决方案(只是无法解决以下标准#7):
select
title, "index", titleLeft,
convert(int, coalesce(nullif(titleRightTrim2, ''), titleRight)) titleRight
from
(select
title, "index", titleLeft, titleRight, titleRightTrim1,
case
when PATINDEX('%[^0-9]%', titleRightTrim2) = 0
then titleRightTrim2
else left(titleRightTrim2, PATINDEX('%[^0-9]%', titleRightTrim2) - 1)
end as titleRightTrim2
from
(select
title,
len(title) - PATINDEX('%[0-9] %', reverse(title)) 'index',
left(title, len(title) - PATINDEX('%[0-9] %', reverse(title))) titleLeft,
ltrim(right(title, PATINDEX('%[0-9] %', reverse(title)))) titleRight,
ltrim(right(title, PATINDEX('%[0-9] %', reverse(title)))) titleRightTrim1,
left(ltrim(right(title, PATINDEX('%[0-9] %', reverse(title)))), PATINDEX('% %', ltrim(right(title, PATINDEX('%[0-9] %', reverse(title)))))) titleRightTrim2
from
tvseason) x) y
order by
titleLeft, titleRight
需要考虑的标准:
- 文本不包含数字
- 文本以数字开头和结尾
- 文本只以数字开头
- 文本只以数字结尾
- 文本可能以(YYYY)结尾
- 文本可能以单个数字或双位数字结尾(例如1或01)
- 可选:以上任意组合,加上文本中间的数字
以下是输出结果:
title
100 Season 1
100 Season 2
100 Season 03
100 Season 4
100 Season 10
**Case 7 here**
Another 10th Anniversary Season 01
Another 1st Anniversary Season 01
Another 2nd Anniversary Season 01
Another Season 01
Another Season 02
Show (2008) Season 1
Show (2008) Season 2
Show 2 The 75th Anniversary Season 1
Show Season 1 (2008)
Show Season 2 (2008)
Show Season 10 (2008)
Some Show Another No Season Number
Some Show No Season Number
Some Show With Season Number 1
Some Show With Season Number 2
Some Show With Season Number 10