You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

SQL关联查询中如何仅在首次出现时展示child.col字段重复值

实现方案

你可以用标准SQL支持的ROW_NUMBER()窗口函数实现需求,对原有复杂查询的侵入性极低,只需要将原有查询作为子查询嵌套即可。

核心逻辑说明

  • 用PARTITION BY child.name将相同子项的行划分为同一组
  • 用ORDER BY指定你判定「首次出现」的排序规则(示例中按parent.name排序,你可以根据业务替换为创建时间、ID等字段)
  • 用CASE语句判断组内行序号为1时返回child.col的值,否则返回空值

代码实现

基础版本(兼容所有支持窗口函数的数据库:MySQL8+、PostgreSQL、SQL Server、Oracle等)

如果需要先得到带instance序号的结果:

SELECT 
  parent.name,
  child.name,
  child.col,
  ROW_NUMBER() OVER (PARTITION BY child.name ORDER BY parent.name) AS instance
FROM parent
JOIN child ON parent.match = child.match

如果直接得到仅首次展示child.col的最终结果:

SELECT 
  parent.name,
  child.name,
  CASE 
    WHEN ROW_NUMBER() OVER (PARTITION BY child.name ORDER BY parent.name) = 1 
    THEN child.col 
    ELSE NULL -- 如需显示空字符串可替换为 ''
  END AS child_col
FROM parent
JOIN child ON parent.match = child.match

适配复杂查询的写法

如果你的原有查询逻辑非常复杂,不需要修改原有逻辑,直接将其作为子查询嵌套即可:

SELECT
  name,
  child_name,
  CASE WHEN rn = 1 THEN child_col ELSE NULL END AS child_col
FROM (
  SELECT 
    *,
    ROW_NUMBER() OVER (PARTITION BY child_name ORDER BY 你业务中判定首次出现的排序字段) AS rn
  FROM (
    -- 此处直接粘贴你原有复杂查询的完整代码即可
    SELECT ... 原有复杂查询逻辑 ...
  ) origin_query
) t

MySQL 5.x兼容版本(不支持窗口函数的场景)

SELECT 
  name,
  child_name,
  CASE WHEN @prev_child = child_name THEN NULL ELSE child_col END AS child_col,
  @prev_child := child_name
FROM (
  -- 先排序,优先按child.name分组,再按首次出现规则排序
  SELECT parent.name, child.name AS child_name, child.col AS child_col
  FROM parent
  JOIN child ON parent.match = child.match
  ORDER BY child.name, parent.name
) t, (SELECT @prev_child := '') AS init

内容的提问来源于stack exchange,提问作者GammaGames

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.10.06 05:54:03