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

SQL多表关联问题:获取客户最新创建地址的TOP1关联实现

我来帮你搞定这个查询问题!你遇到的关联困扰大概率是没处理好「一个客户对应多个地址」的场景——毕竟要筛选出最新创建的那条地址,得先给每个客户的地址做个排序筛选,再和主表关联才行。

下面给你两种常用的解决方案,都是针对你的表结构设计的:


方案1:用窗口函数(推荐,逻辑清晰易维护)

窗口函数可以轻松给每个客户的地址按创建时间排序,直接取最新的那条:

WITH CustomerLatestLocations AS (
    SELECT 
        cl.CustomerID,
        l.LocationID,
        l.StreetAddress1,
        l.StreetAddress2,
        l.City,
        l.State,
        l.Zip,
        l.Country,
        l.CreatedDate,
        -- 按客户分组,地址按创建时间倒序排,最新的地址标记为1
        ROW_NUMBER() OVER (PARTITION BY cl.CustomerID ORDER BY l.CreatedDate DESC) AS rn
    FROM CustomerLocations cl
    JOIN Locations l ON cl.LocationID = l.LocationID
)
SELECT 
    c.CustomerID,
    CONCAT(c.FirstName, ' ', c.LastName) AS CustomerName,
    cll.StreetAddress1,
    cll.StreetAddress2,
    cll.City,
    cll.State,
    cll.Zip,
    cll.Country,
    cll.CreatedDate AS LatestAddressCreatedDate
FROM Customers c
-- 用LEFT JOIN保留没有地址的客户,不需要的话换成INNER JOIN
LEFT JOIN CustomerLatestLocations cll ON c.CustomerID = cll.CustomerID AND cll.rn = 1
ORDER BY c.CustomerID;

逻辑说明:

  1. 先通过CTE(临时结果集)关联CustomerLocations和Locations,给每个客户的地址按CreatedDate倒序编号;
  2. 主查询里只取编号为1的地址(也就是最新的那条),和Customers表关联得到最终结果。

方案2:用子查询筛选最新地址

如果你的数据库不支持窗口函数(比如老版本MySQL),可以用子查询先找到每个客户的最新地址创建时间,再关联回去:

SELECT 
    c.CustomerID,
    CONCAT(c.FirstName, ' ', c.LastName) AS CustomerName,
    l.StreetAddress1,
    l.StreetAddress2,
    l.City,
    l.State,
    l.Zip,
    l.Country,
    l.CreatedDate AS LatestAddressCreatedDate
FROM Customers c
LEFT JOIN (
    SELECT 
        cl.CustomerID,
        l.*
    FROM CustomerLocations cl
    JOIN Locations l ON cl.LocationID = l.LocationID
    WHERE (cl.CustomerID, l.CreatedDate) IN (
        -- 先找出每个客户的最新地址创建时间
        SELECT 
            cl_inner.CustomerID,
            MAX(l_inner.CreatedDate)
        FROM CustomerLocations cl_inner
        JOIN Locations l_inner ON cl_inner.LocationID = l_inner.LocationID
        GROUP BY cl_inner.CustomerID
    )
) l ON c.CustomerID = l.CustomerID
ORDER BY c.CustomerID;

注意:

如果一个客户在同一时间创建了多个地址,这个方案会返回多条记录;而方案1的窗口函数可以通过调整排序条件(比如加上l.LocationID DESC)来确保只返回一条。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.05.22 09:44:45