【问题标题】:Why do these queries return differently?为什么这些查询返回不同?
【发布时间】:2015-04-28 12:56:12
【问题描述】:

我正在处理一个查询,我正在更新一个始终有 1 行的用户定义表(它是更大操作的一部分)。该表是通过根据员工 ID 从更大的员工表中查询来填充的。

这个查询大部分时间都在工作,但在某些情况下我得到一个

'子查询返回超过 1 个值。这是不允许的,当 子查询遵循 =、!=、、>= 或当子查询用作 一个表达式。'

错误。

UPDATE @empInfo SET lastpromotiondate = ISNULL((
SELECT begindate
FROM performanceyear
WHERE lastpromotiondate BETWEEN 
 begindate AND enddate AND performanceyear.[fk_function_id] = 
 functionid AND isfederal = 
 performanceyear.federal), lastpromotiondate)

我无法准确指出原因,我尝试使用 select 填充值,但它只返回 1 个结果。

我不知所措,所以我在下面尝试并成功了。

UPDATE @empInfo SET LastPromotionDate = ISNULL((
SELECT begindate
FROM performanceyear
WHERE (SELECT LastPromotionDate FROM @empinfo) BETWEEN begindate AND enddate 
AND [FK_Function_ID] = (SELECT FunctionID FROM @empinfo) 
AND Federal = (SELECT isFederal FROM @empinfo)
), LastPromotionDate)

它们绝对不会执行相同的操作,但我觉得我在这里遗漏了一些东西。为什么一个有效而另一个无效? @empInfo 只有 1 行。

编辑2:

我似乎认为自己在这个问题上陷入了困境!

返回错误的原始查询是:

UPDATE @empInfo SET LastPromotionDate = 
ISNULL((
SELECT begindate
FROM performanceyear
WHERE LastPromotionDate BETWEEN begindate AND enddate 
AND performanceyear.[FK_Function_ID] = FunctionID 
AND Federal = performanceyear.Federal)
,LastPromotionDate)

@empInfo 有一个 'Federal' 列,当我查看这个执行计划时,'performanceyear' 也是如此,它正在将 'performanceyear'.Federal 与 'performanceyear'.Federal 进行比较。所以我更改了@empInfo Federal 名称,它是Federal,它起作用了。

我的其他测试导致问题的原因不是因为@empinfo 中有 2 行。这是因为我正在运行更新,然后再次更新。第一次更新导致第二次从 performanceyear 返回 2 个结果。

他们独立运行。

话虽如此,我仍然不知道在没有不同名称的列的情况下可以工作的解决方案,因为我不能在更新子查询中的 @empInfo 上使用别名。

【问题讨论】:

  • 添加回车以希望清理查询。
  • 好多了,谢谢。
  • 错误似乎很清楚。您的子查询之一返回超过 1 个值,并且您无法将列与单个值进行比较。你确定@empinfo 只有 1 行吗?否则错误提示。
  • 我 100% 确定它只有 1 行,我在更新前仔细检查了一个选择,它显示了 1 行数据。
  • 也许有一些INSERT 触发器会抛出异常?

标签: sql sql-server sql-update subquery isnull


【解决方案1】:

我怀疑您在 @empInfo 和 performanceyear 之间有一些重复的列名,因为您只是从一个表中选择数据,所以没有警告。如果您使用 tablename.columnname,您可能会修复您的第一个查询。

我会重写你的查询如下(未经测试)

UPDATE ei 
    SET LastPromotionDate = ISNULL(py.begindate, py.LastPromotionDate)
FROM performanceyear py
INNER JOIN @empInfo ei
    ON ei.LastPromotionDate BETWEEN py.begindate AND py.enddate
        AND ei.FunctionID = py.[FK_Function_ID]
        AND ei.isFederal = py.Federal

【讨论】:

  • 就在我写我的更新时,这就是问题所在,我在两次中都有联邦。
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多