从Json字符串中提取数据并分成多列

时间:2018-08-02 18:29:43

标签: json sql-server tsql

我在具有Jsonstring文本的表中有一列:

[
    {
        "PType":{"code":"9","name":"Hospitality"},
        "PSubType":{"code":"901","name":"Hotel"},
        "AType":{"code":"9","name":"Hospitality"},
        "ASubType":{"code":"901","name":"Hotel"}
    }
]

如何使用sql server查询将其分为多列?

2 个答案:

答案 0 :(得分:1)

对于SQL Server 2016+,有native JSON support

DECLARE @json NVARCHAR(MAX)=
N'[
    {
        "PType":{"code":"9","name":"Hospitality"},
        "PSubType":{"code":"901","name":"Hotel"},
        "AType":{"code":"9","name":"Hospitality"},
        "ASubType":{"code":"901","name":"Hotel"}
    }
]';

SELECT A.[key]
      ,JSON_VALUE(A.value,'$.code') AS Code
      ,JSON_VALUE(A.value,'$.name') AS [Name]
FROM OPENJSON(JSON_QUERY(@json,'$[0]')) A;

结果

key         Code    Name
---------------------------------
PType       9       Hospitality
PSubType    901     Hotel
AType       9       Hospitality
ASubType    901     Hotel

一些解释:

使用JSON_QUERY()可以在数组中获取元素,OPENJSON将查找其中的所有对象并将它们作为派生表返回。

JSON_VALUE将内部内容读入列。

提示

v2016以下的版本,您应该使用其他工具或考虑CLR功能...

答案 1 :(得分:0)

在SQL Server 2016+中,您可以结合使用openjson(更多信息here)和cross apply

declare @json nvarchar(max) = '[ { "PType":{"code":"9","name":"Hospitality"}, "PSubType":{"code":"901","name":"Hotel"}, "AType":{"code":"9","name":"Hospitality"}, "ASubType":{"code":"901","name":"Hotel"} } ]'

select
 [PT].[code] as Ptype_Code
,[PT].[name] as Ptype_Name
,[PS].[code] as PSubType_Code
,[PS].[name] as PSubType_Name
,[AT].[code] as AType_Code
,[AT].[name] as AType_Name
,[AS].[code] as ASubType_Code
,[AS].[name] as ASubType_Name

from   openjson (@json)
with
(
    PType  nvarchar(max) as json,
    PSubType  nvarchar(max) as json,
    AType  nvarchar(max) as json,
    ASubType  nvarchar(max) as json
) as lev1
cross apply openjson (lev1.PType)
with
(
    code int,
    name nvarchar(100)
) as PT
cross apply openjson (lev1.PSubType)
with
(
    code int,
    name nvarchar(100)
) as PS
cross apply openjson (lev1.AType)
with
(
    code int,
    name nvarchar(100)
) as [AT]
cross apply openjson (lev1.ASubType)
with
(
    code int,
    name nvarchar(100)
) as [AS]

结果:

enter image description here