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

SQL Server中多行合并为单行的实现方法及SQL代码解析

一、SQL Server 中将多行数据合并为单行的常用方法

在SQL Server里,把多行数据合并成单行字符串是非常常见的需求,我整理了几种实用方案,适配不同版本的SQL Server:

1. STRING_AGG(SQL Server 2017 及以上版本)

这是官方推荐的简洁方法,内置函数直接搞定,语法直观。比如要把同一部门的员工姓名合并成逗号分隔的字符串:

SELECT 
    DepartmentID,
    STRING_AGG(EmployeeName, ', ') AS EmployeeList
FROM Employees
GROUP BY DepartmentID;

如果需要指定合并后的排序顺序,可以加WITHIN GROUP子句:

SELECT 
    DepartmentID,
    STRING_AGG(EmployeeName, ', ') WITHIN GROUP (ORDER BY EmployeeName ASC) AS SortedEmployeeList
FROM Employees
GROUP BY DepartmentID;

2. FOR XML PATH + STUFF(兼容SQL Server 2008及以上低版本)

如果你的数据库版本不支持STRING_AGG,这个经典组合绝对靠谱。还是用上面的员工例子:

SELECT 
    DepartmentID,
    STUFF(
        (SELECT ', ' + EmployeeName 
         FROM Employees e2 
         WHERE e2.DepartmentID = e1.DepartmentID
         FOR XML PATH(''), TYPE).value('.', 'NVARCHAR(MAX)'),
        1, 2, ''
    ) AS EmployeeList
FROM Employees e1
GROUP BY DepartmentID;

简单解释下:FOR XML PATH('')会把查询结果拼接成XML字符串,TYPE让它返回XML类型,.value('.', 'NVARCHAR(MAX)')把XML转成普通字符串,STUFF则用来去掉开头多余的分隔符(这里是, ,所以从第1位开始删除2个字符)。

3. COALESCE 变量拼接(适合单分组场景)

如果只是要把某一个分组的多行数据拼成字符串,用变量加COALESCE也很方便:

DECLARE @EmployeeList NVARCHAR(MAX) = '';
SELECT @EmployeeList = COALESCE(@EmployeeList + ', ', '') + EmployeeName
FROM Employees
WHERE DepartmentID = 1;
SELECT @EmployeeList AS EmployeeList;

不过这种方法批量处理多分组时效率不如前两种,适合单分组的简单场景。


二、给定SQL查询代码的功能解析

先把你提供的截断代码整理完整(补全合理的截断部分):

DECLARE @Count BIGINT 
SELECT @Count = Count(ID) FROM Users; 

SELECT TOP 50 
    CustUser.[ID], 
    CustUser.[FirstName] + ' ' + CustUser.[LastName] FirstName, 
    CustUser.[NickName], 
    CustUser.[UserName], 
    R.[Name] Roles 
FROM (
    SELECT 
        ROW_NUMBER() OVER(ORDER BY US.ID Desc) AS Row, 
        US.[ID], 
        US.[FirstName], 
        US.[LastName], 
        US.[NickName], 
        US.[UserName], 
        US.[Password] 
    FROM [Users] US
) CustUser 
LEFT JOIN Category CL ON CustUser.[LoginModeCode] = CL.CategoryCode 
LEFT JOIN Category CS ON CustUser.[StatusCode] = CS.CategoryCode
LEFT JOIN Roles R ON CustUser.RoleID = R.ID -- 补全合理的角色关联逻辑

现在逐段解析功能:

  1. 变量声明与统计(冗余/未使用):

    • DECLARE @Count BIGINT:声明一个大整数类型的变量@Count
    • SELECT @Count = Count(ID) FROM Users:统计Users表的总用户数并赋值给@Count,但这段代码里@Count后续没有被调用,大概率是残留代码,或者原本有分页计算(比如总页数)的逻辑被截断了。
  2. 子查询CustUser:

    • 用ROW_NUMBER() OVER(ORDER BY US.ID Desc)给Users表的每一行按ID降序生成行号Row,同时取出用户的核心字段:ID、姓名、昵称、用户名、密码。这个子查询的作用是给用户数据做排序标记,方便后续分页或筛选。
  3. 外层查询与关联逻辑:

    • SELECT TOP 50:只返回最新的50条用户数据(因为子查询按ID降序排序,ID大的是最新数据)
    • 拼接用户的FirstName和LastName成一个新的FirstName字段(这里字段名和原字段重名,建议改成FullName更清晰)
    • 两次左连Category表:
      • 第一次通过LoginModeCode关联,目的是获取用户登录模式的分类名称(比如密码登录、短信登录等),但代码里没选择该表的字段,属于截断遗漏
      • 第二次通过StatusCode关联,目的是获取用户状态的分类名称(比如正常、禁用等),同样遗漏了字段选择
    • 左连Roles表(补全的合理逻辑):通过用户的角色ID关联,获取用户对应的角色名称,最终在结果中返回为Roles字段。
  4. 整体核心逻辑:
    这段代码的核心是从Users表中获取最新的50条用户数据,同时关联分类表获取登录模式、用户状态的分类信息,关联角色表获取用户角色,最终返回用户的ID、全名、昵称、用户名、角色等关键信息。


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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.05.26 08:41:05