我在SQL列中有以下数据。列类型是String。当我从数据库中查询数据时,我更愿意对这些数据进行排序,但我想在SQL查询完成后可以使用一些Ruby魔法进行组织。还有其他列被拔出,因此这只是需要排序的列之一。
Expenses
$3500/MONTH
$1,000.00
STANDARD CONTRACTOR
$5,000.00
数据无法更改,必须存储在同一列中(上例中只是测试数据)。
我想通过增加数字和其余(字符串)值来组织数据。预期结果应为:
$1,000.00
$5,000.00
$3500/MONTH
STANDARD CONTRACTOR
或
$1,000.00
$5,000.00
STANDARD CONTRACTOR
$3500/MONTH
答案 0 :(得分:1)
选项1(fiddle here):
select expenses from table1
order by
replace(replace(expenses, "$", ""), ",", "") regexp "[0-9.]*" desc,
case when replace(replace(expenses, "$", ""), ",", "") regexp "[0-9.]*"
then cast(replace(replace(expenses, "$", ""), ",", "") as real)
else 0
end
选项2(fiddle here):
select expenses from (
select expenses,
replace(replace(expenses, "$", ""), ",", "") expensesNormalized
from table1
) s
order by
expensesNormalized regexp "[0-9.]*" desc,
case when expensesNormalized regexp "[0-9.]*"
then cast(expensesNormalized as real)
else 0
end
去哪个跑得更快。
答案 1 :(得分:0)
在SQL Server中,您可以执行以下操作:
order by (case when isnumeric(col) = 1 then 1 else 0 end) desc,
(case when isnumeric(col) = 1 then cast(col as money) end),
col
对于其他数据库,您可以使用正则表达式匹配而不是isnumeric来确定哪些是数字。
由于您使用的是SQLite,我似乎可以假设所有数字都以'$'开头,所以这样的东西几乎可以工作:
order by (case when substr(col, 1, 1) = '$' then 1 else 0 end) desc,
(case when substr(col, 1, 1) = '$' then cast(col as numeric) end),
col
问题是“3,500美元/月”被视为一个数字。你可以使用regexp解决这个问题,如果你有的话。或者,如果“/”定义了这些情况,您可以使用以下特定内容:
order by (case when substr(col, 1, 1) = '$' and col not like '%/%' then 1 else 0 end) desc,
(case when substr(col, 1, 1) = '$' and col not like '%/%' then cast(col as numeric) end),
col
答案 2 :(得分:0)
如果现有的答案在SQLlite中有效,那么它们可能适合您。因为数据非常......凌乱......我倾向于尝试将这个丑陋的部分封装在一个返回排序数组的方法中。
如果你有这么少的行(例如少于500行),那么更简洁的排序方法是包括Comparable并编写一个自定义比较器,如nicely documented in this SO answer。