【问题标题】:Turn Cross Apply opensjson results into columns将 Cross Apply opensjson 结果转成列
【发布时间】:2021-11-10 18:39:47
【问题描述】:

我们有一个表,其中有一个带有一些 json 的字段。 使用 cross apply 我能够将这些对变成列:

select [mytable].ID,[mytable].[IndexFields],  jsonvalues.[Key], jsonvalues.[Value]

from [mytable]

cross APPLY OPENJSON([mytable].[IndexFields])
WITH
([Key] nvarchar(255) ,
[Value] nvarchar(255) ) as jsonValues
order by [mytable].ID

那么我该如何把它变成这样的东西:

谢谢。

【问题讨论】:

  • 您是否提前知道所有可能的键名(名字、姓氏、MyChoice 等)?还是需要针对添加的每个新键进行调整?另外,请将表结构和示例数据作为插入(例如,使用db<>fiddle 并选择正确版本的 SQL Server)而不是图片。
  • 查看条件聚合或透视。

标签: sql arrays json sql-server


【解决方案1】:

如果您事先知道有限的一组可能的键名,您可以使用PIVOT

;WITH src AS 
(
  select [mytable].ID,[mytable].[IndexFields],
    jsonvalues.[Key], jsonvalues.[Value]
    from dbo.[mytable]
    cross APPLY OPENJSON([mytable].[IndexFields])
    WITH
    ([Key] nvarchar(255) , 
    [Value] nvarchar(255) ) as jsonValues
)
SELECT * FROM src
  PIVOT (
    MAX(Value) FOR [Key] IN 
    ([firstname],[lastname],[MyChoice],[Optional Coverages])
  ) AS p
ORDER BY src.ID;

但是,如果您事先不知道所有这些可能的值,就不能写PIVOT。所以它有点复杂,需要动态 SQL(我写了an article about dynamic PIVOT here):

DECLARE @keys nvarchar(max);

SELECT @keys = STRING_AGG('[' + STRING_ESCAPE([Key], 'json') + ']', ',')
FROM 
(
  SELECT j.[Key]
    FROM dbo.mytable AS t
    CROSS APPLY OPENJSON(t.IndexFields)
    WITH
    (
      [Key]   nvarchar(255),
      [Value] nvarchar(255) 
    ) AS j
    GROUP BY j.[Key]
) AS x;

DECLARE @sql nvarchar(max) = N'
;WITH src AS 
(
  SELECT t.ID, t.IndexFields, j.[Key], j.[Value]
    FROM dbo.mytable AS t
    CROSS APPLY OPENJSON(t.IndexFields)
    WITH
    (
      [Key]   nvarchar(255),
      [Value] nvarchar(255) 
    ) AS j
)
SELECT * FROM src
PIVOT (MAX(Value) FOR [Key] IN (' + @keys + N')) AS p
ORDER BY ID;';

EXEC sys.sp_executesql @sql;

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2015-03-25
    • 1970-01-01
    • 2022-01-01
    • 1970-01-01
    • 2013-04-28
    • 1970-01-01
    • 2011-10-07
    相关资源
    最近更新 更多