首页 > 解决方案 > 当存在 NULL 时执行 ORDER BY CAST

问题描述

我有一个表有一个包含数字或 NULL 的列。它是一个名为 details.col_rating 的 (VARCHAR(255),Null) 列

我希望运行一个查询,在其中选择值大于 165 的任何记录

该查询连接 2 个表。

主表有比赛的详细信息。

• col_id 具有每个独特种族的编号。

• col_racedesc 有比赛名称

• col_course 是比赛所在的赛道

• col_type 的比赛类型代码为空白、h、b 或 c

表格详细信息包含每场比赛的马匹详细信息。

• col_maind 是主表中的 col_id

• col_fpos 是比赛的终点位置

• col_rating 是授予马匹的数字。

我会用这样的东西开始查询。

SELECT details.col_mainid, 
       details.col_fpos, 
       details.col_rating, 
       main.col_type,
       main.col_racedesc, 
       main.col_course,
FROM main
     INNER JOIN details on main.col_id = details.col_mainid
WHERE details.col_rating >'165'
  and main.col_type ='h'
ORDER BY CAST (details.col_rating as INT) DESC

但是,将 varchar 值“Null”转换为数据类型 int 时,我只是收到一个错误转换失败。如何在使用 col_rating 数据时按数字顺序进行 Order 并忽略 NULL 条目

标签: sql-server

解决方案


这里真正的问题是你的设计。似乎您将数字数据存储在varchar(第一个错误的事情)中,并存储字符串value'Null'而不是 value NULL'Null'因此,如果修复设计并停止使用字符串来表示,您真正需要做什么NULL'Null'NULL不一样。NULL代表一个未知值,只能与使用比较IS (NOT) NULL'Null'varchar长度为4的a,并且'Null' = 'Null'是真的。不要存储字符串而不是NULL它们的行为不同。)

首先,您可以摆脱这些'Null'价值观。此外,我们应该摆脱任何其他不良价值观。我们可以使用TRY_CONVERT

--Make sure you have a backup ready, just in case!
UPDATE dbo.details
SET col_rating = TRY_CONVERT(int,col_rating);

现在我们可以修复您的数据类型:

ALTER TABLE dbo.details ALTER COLUMN col_rating int NULL;

现在您可以运行查询而不会出错:

sELECT d.col_mainid, 
       d.col_fpos, 
       d.col_rating, 
       m.col_type,
       m.col_racedesc, 
       m.col_course,
FROM main m
     INNER JOIN details d ON m.col_id = d.col_mainid
WHERE d.col_rating > 165
  AND m.col_type ='h'
ORDER BY d.col_rating DESC;

推荐阅读