SQL字母数字值之间

时间:2013-10-11 04:45:17

标签: sql-server-2008-r2

我的db表中有一个字母数字列。对于我的过滤器,我用它来获取结果过滤器值。一切正常。但是,在某些情况下,它错过了一些来自过滤的数据。这是我的样本,

示例数据

ACQPO14
002421
ACQPO8
ACQPO14
ACQPO19
DUMMY0001

Sql Query

SELECT po.No,
   po.PoS
FROM PoDetails pod
INNER JOIN Pors po ON po.Id=PoD.PoId
WHERE po.No BETWEEN 'ACQPO1' AND 'ACQPO20'

对于上述样本。查询仅返回 ACQPO14 ACQPO19 ACQPO8

对此问题的任何帮助将不胜感激。

由于

5 个答案:

答案 0 :(得分:1)

这很有道理,因为它只是文字。

1出现在8之前,因此,在文本中排序(从左到右)数据库将忽略ACQPO14的最后一位数字,将其与ACQPO8进行比较。因此ACQPO14已删除)在ACQPO8之前发布,而ACQPO20已删除)也在ACQPO8之前发布。因此它会被between过滤掉。

解决此问题的唯一方法是通过拆分来解析列。 EG:如果ACQPO是一个固定长度的前缀,你可以使用一些DBMS函数(你没有指定任何东西)修剪那个部分,然后转换成数字格式。然后用数字余数进行比较/过滤。

答案 1 :(得分:0)

这是您在Oracle

中执行此操作的方法
SELECT po.No, po.PoS
FROM PoDetails pod
INNER JOIN Pors po ON po.Id=PoD.PoId
WHERE SUBSTR(po.No, 1, 5) = 'ACPQO'
 AND TO_NUMBER(SUBSTR(po.No, 6, 2)) >= 1
 AND TO_NUMBER(SUBSTR(po.No, 6, 2)) <= 20;

首先SUBSTR()用于匹配值的文本部分。然后使用TO_NUMBER()将值的数字部分解析为数字,并使其可用于120之间的数值比较。 (其他数据库也可以使用类似的功能。)

答案 2 :(得分:0)

如果修复了ACQPO,请在SQL Server中尝试以下

SELECT po.No, po.PoS
FROM PoDetails pod
INNER JOIN Pors po ON po.Id=PoD.PoId
WHERE left(po.No,5) and 
cast(substring(po.No,6,len(po.No)) as int)
BETWEEN cast(substring('ACQPO1',6,len(po.No)) as int)  AND cast(substring('ACQPO20',6,len(po.No)) as int)


SELECT substring(data,6,len(data)),* FROM #Temp Where 
left(data,5) ='ACQPO' And 
cast(substring(data,6,len(data)) as int)
BETWEEN cast(substring('ACQPO1',6,len(data)) as int)  AND cast(substring('ACQPO20',6,len(data)) as int)

答案 3 :(得分:0)

对于 MYSQL:-

SELECT * FROM my_table WHERE SUBSTR(seq_num, 1,3) = 'ABC' /* 验证前缀码 */ 和 替换(seq_num,'ABC','')> = 61440 和 替换(seq_num,'ABC','')<= 61807

SELECT * FROM my_table WHERE SUBSTR(seq_num, 1,3) = 'ABC' /* 验证前缀码 */ 和 substr(seq_num, 4, 长度(seq_num)) >= 61440 和 SUBSTR(seq_num, 4, LENGTH(seq_num)) <= 61807

适用于(喜欢):

ABC61447, ABC61448, ABC61545, ..., ..., ABC61807

答案 4 :(得分:0)

只需使用范围 10 到 20 即可!

SELECT po.No,
   po.PoS
FROM PoDetails pod
INNER JOIN Pors po ON po.Id=PoD.PoId
WHERE po.No BETWEEN 'ACQPO10' AND 'ACQPO20'