枢轴字段的元数据

时间:2016-02-14 01:30:25

标签: sql types datatable pivot

基于复杂的数据库设置,我有一个复杂的问题。

我有一个包含fieldId,objectId,fieldValue的表。 每个对象在此表中有许多行 - 每个字段占一行。

示例 - 有firstname,dob,weight,height,school等字段

对象(id:1)可以包含以下行:

1.1.'john'
1.2.'march-31-2000'
1.3.155
1.4.60
1.5.'ps 176'

我有一个网格,为每个字段显示一列,每个对象显示一行 - 列名将是firstName,dob,weight,height,school 并且我的数据库中的所有对象都会有行

我使用了一个数据透镜来获取这些数据 -

之类的东西 -

SELECT *
  FROM #temp123
 PIVOT (
          MAX(fieldValue)
          FOR [Variable] IN ([firstName],[dob],[weight],[height],[school])
       ) AS p

这适用于显示数据。但是,现在是时候将排序添加到我的网格中了。我希望int列像int(101> 99)一样排序,日期列显示为日期(2016年1月1日> 2015年12月31日)

我怎样才能做到这一点。

谢谢!

1 个答案:

答案 0 :(得分:1)

这可能是您的解决方案:

CREATE TABLE #EntityAttributValue (entityID INT, Attribute VARCHAR(100),Value VARCHAR(100));
INSERT INTO #EntityAttributValue VALUES
 (1,'BirthDate','2000-04-01')
,(1,'Size','1.72')
,(1,'FirstName','John')
,(1,'LastName','Doe')
,(2,'BirthDate','1990-04-01')
,(2,'Size','1.81')
,(2,'FirstName','Jane')
,(2,'LastName','Miller')
,(3,'BirthDate','1980-05-01')
,(3,'FirstName','Hugo')
,(3,'LastName','Boss');

DECLARE @columns VARCHAR(MAX)=
(
    SELECT STUFF(
    (
    SELECT DISTINCT ',[' + Attribute + ']' 
    FROM #EntityAttributValue
    FOR XML PATH('')
    ),1,1,'')

);

DECLARE @query VARCHAR(MAX)=
'SELECT p.*
FROM
(
    SELECT *
    FROM #EntityAttributValue
) AS tbl
PIVOT
(
    MIN(Value) FOR Attribute IN(' + @columns + ')
) AS p';

--The column's list might be generated from metadata (dictionary attrib/type)
DECLARE @Wrapped VARCHAR(MAX)=
';WITH MyCTE AS (' +  @query + ')
SELECT  entityID
       ,CAST(BirthDate AS DATE) AS BirthDate
       ,FirstName
       ,LastName
       ,CAST(Size AS FLOAT) AS Size
FROM MyCTE';

EXEC (@Wrapped);

GO
DROP TABLE #EntityAttributValue;

这是前一个答案

名称 - 值 - 对(或实体 - 属性 - 值表[EAV])通常是一个不应该做的事情......这是一篇文章(你会发现更多!)描述为什么:http://www.sturnus.co.uk/performance/2008-07/the-curse-of-the-name-value-pair/

如果您必须坚持使用此设计,则CASE使用GROUP BY时会有一个解决方案,但您必须确保您的值正确投放(特别注意日期时间)值):

DECLARE @EntityAttributValue TABLE(entityID INT, Attribute VARCHAR(100),Value VARCHAR(100));
INSERT INTO @EntityAttributValue VALUES
 (1,'BirthDate','2000-04-01')
,(1,'Size','1.72')
,(1,'FirstName','John')
,(1,'LastName','Doe')
,(2,'BirthDate','1990-04-01')
,(2,'Size','1.81')
,(2,'FirstName','Jane')
,(2,'LastName','Miller')
,(3,'BirthDate','1980-05-01')
,(3,'FirstName','Hugo')
,(3,'LastName','Boss');

SELECT eav.entityID
      ,MAX(CASE WHEN eav.Attribute='FirstName' THEN eav.Value ELSE NULL END) AS FirstName
      ,MAX(CASE WHEN eav.Attribute='LastName' THEN eav.Value ELSE NULL END) AS LastName
      ,MAX(CASE WHEN eav.Attribute='BirthDate' THEN CAST(eav.Value AS DATE) ELSE NULL END) AS Birtdate
      ,MAX(CASE WHEN eav.Attribute='Size' THEN CAST(eav.Value AS FLOAT) ELSE NULL END) AS Size
FROM @EntityAttributValue AS eav
GROUP BY eav.entityID