【问题标题】:SQL Unpivot with CASE and LIKE StatementSQL Unpivot 与 CASE 和 LIKE 语句
【发布时间】:2021-06-23 10:03:13
【问题描述】:

寻求一些帮助以 UNPIVOT 类似于所附图像的表格。 我有两种类型的列名,标题中带有“Sales”或“Staff”,我想将它们合并到仅用于 Sales 和 Staff 的列中。 理想情况下,这将是动态完成的,因此我没有指定单独的列名,而只是我正在搜索的标准。 该区域也可以是动态的,也可以通过加入一个单独的 metric -> region 映射表来完成。

【问题讨论】:

  • 或许UNION ALL?
  • 用您正在使用的数据库标记您的问题。

标签: sql dynamic unpivot


【解决方案1】:

通用解决方案使用union all:

select period, channel, 'East' as region, east_sales as sales, east_staff as staff
from t
union all
select period, channel, 'West' as region, west_sales as sales, west_start as staff
from t;

但是,在支持横向连接的数据库中,我建议改为使用横向连接。

【讨论】:

  • 如果这是一个简单的数据集,是的,但实际上这将有数百列,所有列都有“员工”或“销售”(作为示例) - 所以我想避免具体列名 - 区域也是如此
  • @JDR 。 . .您知道给定表中的列是什么——除非您的数据处理环境出现严重异常。如果问题只是输入一堆东西,您可以查询元数据表来构造查询。
【解决方案2】:

您可以使用unpivot,如下所示:

    DECLARE 
      @col_Sales  NVARCHAR(MAX) = N'',
      @col_Staff  NVARCHAR(MAX) = N'',
      @sql        NVARCHAR(MAX) = N'';

--different types of columns extraction

    SELECT @col_Sales += ',' + QUOTENAME(name) 
    FROM sys.columns
    WHERE [object_id] = OBJECT_ID('temptable')
    AND name like '%Sales%';
    
    SELECT @col_Staff += ', ' + QUOTENAME(name)
    FROM sys.columns
    WHERE [object_id] = OBJECT_ID('temptable')
    AND name like '%Staff%';

--dynamic sql
   
    SET @sql = N'SELECT [Period], Channel, replace(Region, ''_Sales'', '''') as Region, Staff, Sales
    FROM
    (
      SELECT *
       FROM temptable
    ) AS t
    UNPIVOT
    (
      Sales FOR Region IN (' + STUFF(@col_Sales, 1, 1, '') + ')
    ) AS up1
    UNPIVOT
    (
      Staff FOR Staffs IN (' + STUFF(@col_Staff, 1, 1, '') + ')
    ) AS up2
    
    where replace(Region, ''sales'','''') = replace(Staffs, ''staff'','''')  --crucial condition
    ;';
    PRINT @sql;
    exec sp_executesql @sql;

请找到 dbfiddle here

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2011-10-08
    • 1970-01-01
    • 2012-01-07
    • 2023-03-12
    • 1970-01-01
    • 2020-01-17
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多