我有一个语句选择charindex的子字符串,如下所示:

SELECT SUBSTRING(StringField, 5, CHARINDEX('ABC', StringField) - 5)...
WHERE
CHARINDEX('ABC', StringField) > 5

当我在select查询中运行上述语句时,返回的结果很好。在绑定到架构的索引视图中运行上述语句时,会出现以下错误:
Invalid length parameter passed to the LEFT or SUBSTRING function

为了解决这个问题,我将编写一个函数来获取charindex的最大值,并删除负值的可能性。但是有人知道where子句为什么不过滤select语句吗?

最佳答案

因为不能保证查询中后台操作的顺序。
我猜如果你检查执行计划,你会发现它同时执行两个检查——这是因为两个操作都不能使用索引!
sql无论如何都需要将该字段的每一行加载到内存中,因此它同时处理这两个条件。
您可以尝试将WITH (MAXDOP(1))作为查询提示,以查看这是否阻止问题出现,或者您可以执行子选择以强制执行顺序:

SELECT SUBSTRING(StringField, 5, CHARINDEX('ABC', StringField) - 5)...
FROM (
      SELECT Stringfield
      FROM Table
      WHERE CHARINDEX('ABC', StringField) > 5
      ) as [X]

有一次,当我使用PATINDEX检查字段是否是数值时,我遇到了类似的问题,我视图中的一列正在将其转换为int-我得到了转换错误,因为引擎正在转换每一行,因为我的筛选器不可搜索。

10-07 13:39