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

多项目客户取最低Rank,单项目客户保留数据的SQL查询需求

解决方案

问题分析

你遇到的核心问题是:用常规分组/窗口函数筛选最低Rank时,单项目且Rank为Null的记录会因Null无法参与等值比较(SQL中Null = 任何值都返回Unknown,会被WHERE条件过滤)而丢失。

方法一:窗口函数+条件筛选

通过窗口函数先统计每个客户的项目数,同时计算其最低Rank,再根据项目数分支处理:

WITH ClientProjectMetrics AS (
    SELECT 
        ClientKey,
        ProjectKey,
        Rank,
        -- 统计当前客户的项目总数
        COUNT(ProjectKey) OVER (PARTITION BY ClientKey) AS TotalProjects,
        -- 计算当前客户的最低Rank(自动忽略Null,若全为Null则返回Null)
        MIN(Rank) OVER (PARTITION BY ClientKey) AS MinRank
    FROM YourTableName
)
SELECT 
    ClientKey,
    ProjectKey,
    Rank
FROM ClientProjectMetrics
WHERE 
    -- 单项目客户:直接保留所有记录(包括Rank为Null的)
    TotalProjects = 1
    -- 多项目客户:仅保留Rank等于最低Rank的记录,同时兼容全Null的情况
    OR (TotalProjects > 1 AND (Rank = MinRank OR (MinRank IS NULL AND Rank IS NULL)))

方法二:LEFT JOIN聚合结果

如果你不习惯用CTE,也可以通过左关联客户的聚合统计结果来实现,避免INNER JOIN导致的记录丢失:

SELECT 
    t.ClientKey,
    t.ProjectKey,
    t.Rank
FROM YourTableName t
LEFT JOIN (
    SELECT 
        ClientKey,
        COUNT(ProjectKey) AS TotalProjects,
        MIN(Rank) AS MinRank
    FROM YourTableName
    GROUP BY ClientKey
) c_stats ON t.ClientKey = c_stats.ClientKey
WHERE 
    c_stats.TotalProjects = 1
    OR (c_stats.TotalProjects > 1 AND (t.Rank = c_stats.MinRank OR (c_stats.MinRank IS NULL AND t.Rank IS NULL)))

关键注意点

  • 必须用LEFT JOIN而非INNER JOIN,否则单项目且Rank为Null的客户会因为聚合子查询中MIN(Rank)为Null而被过滤。
  • 处理多项目且全Rank为Null的场景:必须单独判断MinRank IS NULL AND Rank IS NULL,因为SQL中Null = Null不成立,无法通过等值比较匹配。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.08.01 22:40:24