【问题标题】:if "Subquery returns more than 1 row" consider it NULL如果“子查询返回超过 1 行”认为它为 NULL
【发布时间】:2011-10-04 03:36:30
【问题描述】:

我正在尝试将 newtable 上的 store id 与 maintable 中的 id 同步:

UPDATE newtable t SET t.store_id = (SELECT store_id FROM maintable s 
WHERE t.state = s.state AND s.city = t.city AND t.name = s.name)

当子查询返回多于一行时,它会出错,并显示“子查询返回多于 1 行”,但是当它返回零行时,子查询被认为没有返回任何内容,因此 newtable 上的 store_id 保持为 NULL。这里没有什么新东西,它就是它的工作原理。

我想知道是否可以让子查询的输出与当它有多个匹配行时没有匹配时的输出相同。

这样,我将只为主表上的一个匹配行同步 store_id,并在子查询中出现多个匹配行时跳过。

【问题讨论】:

  • 如果SELECT store_id 产生一个值,则将t.store_id 设置为该值;如果它没有产生任何结果,则将 t.store_id 设置为 NULL;如果它产生多个值,则将 t.store_id 设置为 NULL。对吗?
  • @mu 太短:我想当返回多个值时,他只想丢弃重复的值,只将其中一个存储在store_id 中,当什么都不返回时,他想要存储一个默认值。
  • @Sayem:那是我不清楚的,问题的最后两段似乎在说不同的东西。
  • 我来了!我的意思是@mu 太短了。

标签: mysql sql mysql-error-1242


【解决方案1】:
UPDATE newtable t SET t.store_id = IFNULL((SELECT store_id FROM maintable s 
WHERE t.state = s.state AND s.city = t.city AND t.name = s.name HAVING COUNT(*) = 1), t.store_id)

IFNULL(use_this_value_if_not_null,value_if_first_isnull)

【讨论】:

  • 我添加了 HAVING COUNT(*) = 1 就像“@mu 太短”,只是为了有一个完整的解决方案,因为我不确定@mu 答案是否在内部查询返回你想要的 null。
【解决方案2】:

我认为您可能正在寻找一个 HAVING 子句来强制查询匹配一次:

UPDATE newtable t
SET t.store_id = (
    SELECT store_id
    FROM maintable s
    WHERE t.state = s.state
      AND s.city  = t.city
      AND t.name = s.name
    HAVING COUNT(*) = 1
)

这应该使多个匹配的行为与没有匹配的行为相同。 HAVING 子句几乎在查询过程的最后应用;如果 WHERE 没有匹配项或多个匹配项,则 COUNT(*) = 1 将失败,内部查询将不返回任何内容,但如果恰好有一行,则 COUNT(*) = 1 将成功,内部查询将返回该单个匹配项。

【讨论】:

    【解决方案3】:

    您可以考虑在子查询中添加LIMIT 1,以更好地实现您想要完成的任务,具体取决于您的具体需求。

    否则,您应该能够通过 IF 或 CASE 获得创意:

    UPDATE newtable t SET t.store_id = (
        SELECT IF(num>1, NULL, storeid) FROM (
            SELECT COUNT(*) AS num, storeid FROM maintable s WHERE t.state=s.state AND s.city=t.city AND t.name=s.name
        )
    )
    

    未经测试,但应该能让你大致了解。

    【讨论】:

    • LIMIT 1 不是一个选项,因为它不会是精确的 store_id 匹配。我会玩 IF、CASE 并让你知道。
    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多