如何在Sql中将行转换为列
我有一个表如何在Sql中将行转换为列,sql,sql-server,sql-server-2008,tsql,Sql,Sql Server,Sql Server 2008,Tsql,我有一个表列 以及第二个表Response,其中保存了所有数据 现在我想创建一个SQL视图,其中的结果应该如下 ;with cte as ( select r.*, c.name from Response r inner join Columns c on r.columnid = c.id ) select Userid, max([FromDate]) as [FromDate], m
列
以及第二个表Response
,其中保存了所有数据
现在我想创建一个SQL视图,其中的结果应该如下
;with cte as
(
select r.*,
c.name
from Response r
inner join Columns c
on r.columnid = c.id
)
select
Userid,
max([FromDate]) as [FromDate],
max([ToDate]) as [ToDate],
max([Project]) as [Project],
max([Comment]) as [Comment]
from cte
pivot
(
max(Text) for name in ([FromDate], [ToDate], [Project], [Comment])
) p
group by userid
我试着用pivot
select UserId ,FromDate, ToDate, Project, Comment
from
(
select R.UserId ,R.Text , C.ColumnName
from [Columns] C
INNER JOIN Response R ON C.Id=R.ColumnId
) d
pivot
(
max(Text)
for ColumnName in (FromDate, ToDate, Project, Comment)
) piv;
但这对我不起作用,我也提到了这一点,但无法实施。如何在SQL视图中实现同样的功能
表的脚本:
CREATE TABLE [dbo].[Columns](
[Id] [bigint] IDENTITY(1,1) NOT NULL,
[Name] [nvarchar](1000) NULL,
[IsActive] [bit] NULL,
CONSTRAINT [PK_Columns] PRIMARY KEY CLUSTERED
(
[Id] ASC
)WITH (PAD_INDEX = OFF, STATISTICS_NORECOMPUTE = OFF, IGNORE_DUP_KEY = OFF, ALLOW_ROW_LOCKS = ON, ALLOW_PAGE_LOCKS = ON) ON [PRIMARY]
) ON [PRIMARY]
GO
insert into [Columns] values('FromDate',1)
insert into [Columns] values('ToDate',1)
insert into [Columns] values('Project',1)
insert into [Columns] values('Comment',1)
CREATE TABLE [dbo].[Response](
[Id] [bigint] IDENTITY(1,1) NOT NULL,
[UserId] [bigint] NOT NULL,
[ColumnId] [bigint] NOT NULL,
[Text] [nvarchar](max) NULL,
[IsActive] [bit] NULL,
CONSTRAINT [PK_Response] PRIMARY KEY CLUSTERED
(
[Id] ASC
)WITH (PAD_INDEX = OFF, STATISTICS_NORECOMPUTE = OFF, IGNORE_DUP_KEY = OFF, ALLOW_ROW_LOCKS = ON, ALLOW_PAGE_LOCKS = ON) ON [PRIMARY]
) ON [PRIMARY]
GO
insert into [Response] values(1,1,'1/1/2012',1)
insert into [Response] values(1,2,'1/2/2012',1)
insert into [Response] values(1,3,'p1',1)
insert into [Response] values(1,4,'c1',1)
insert into [Response] values(2,1,'1/1/2013',1)
insert into [Response] values(2,2,'1/2/2013',1)
insert into [Response] values(2,3,'p2',1)
insert into [Response] values(2,4,'c2',1)
insert into [Response] values(2,1,'1/1/2014',1)
insert into [Response] values(2,2,'1/2/2014',1)
insert into [Response] values(2,3,'p3',1)
insert into [Response] values(2,4,'c3',1)
insert into [Response] values(3,1,'1/1/2015',1)
insert into [Response] values(3,2,'1/2/2015',1)
insert into [Response] values(3,3,'p4',1)
insert into [Response] values(3,4,'c4',1)
您可以这样查询
;with cte as
(
select r.*,
c.name
from Response r
inner join Columns c
on r.columnid = c.id
)
select
Userid,
max([FromDate]) as [FromDate],
max([ToDate]) as [ToDate],
max([Project]) as [Project],
max([Comment]) as [Comment]
from cte
pivot
(
max(Text) for name in ([FromDate], [ToDate], [Project], [Comment])
) p
group by userid
试试这个。我已经准备好了你的答案
select UserId ,FromDate, ToDate, Project, Comment
from
(
select R.UserId ,R.RText , C.ColumnName
from [Columns] C
INNER JOIN Response R ON C.Id=R.ColumnId
) d
pivot
(
Min(Rtext)
for ColumnName in (FromDate, ToDate, Project, Comment)
) piv
UNION
select UserId ,FromDate, ToDate, Project, Comment
from
(
select R.UserId ,R.RText , C.ColumnName
from [Columns] C
INNER JOIN Response R ON C.Id=R.ColumnId
) d
pivot
(
Max(Rtext)
for ColumnName in (FromDate, ToDate, Project, Comment)
) piv;
老实说,如果列类型不会改变,或者您只需要它们的一个子集,您可以将它们过滤掉,然后加入它们,而不是编写一个透视。我使用cte编写了它,但它们也很容易成为子查询:
;with fd as
(
select
UserID,
[Text] as FromDate,
row_number() over (partition by userID order by ID) as DEDUP
from response
where ColumnID = 1
),
td as
(
select
UserID,
[Text] as ToDate,
row_number() over (partition by userID order by ID) as DEDUP
from response
where ColumnID = 2
),
p as
(
select
UserID,
[Text] as Project,
row_number() over (partition by userID order by ID) as DEDUP
from response
where ColumnID = 3
),
c as
(
select
UserID,
[Text] as Comment,
row_number() over (partition by userID order by ID) as DEDUP
from response
where ColumnID = 4
)
select
fd.*,
td.ToDate,
p.Project,
c.Comment
from fd
inner join td
on fd.UserId = td.UserId
and fd.DEDUP = td.DEDUP
inner join p
on fd.UserId = p.UserId
and fd.DEDUP = p.DEDUP
inner join c
on fd.UserId = c.UserId
and fd.DEDUP = c.DEDUP
显示对您不起作用的内容。您可以显示您尝试使用的pivot查询吗?@WEI_DBA:shared当一个用户ID在多个项目上时会发生什么情况?@DForck42:正如我在问题中提到的所需输出,对应的
用户ID
的每条记录都应该没有重复记录。答案中有两个问题,1
:max
函数为date
类型值返回null,此处为FromDate
和Todate
列<代码>2:对于UserId=2
只返回1行作为脚本提供输入示例数据共享基于输入脚本的脚本支持的答案。这对我来说很好。我没有得到projectp2
的结果,你是真的运行了你在回答中提到的查询,还是只是编辑并发布在这里。另外,我没有否决你的答案。max
和min
函数为日期类型值返回null,这里为FromDate
和Todate
列返回null。另外,对于UserId=2,您只考虑两行,对于任何UserIdTrue,可以有更多行。我是根据您的数据进行查询的。您的查询返回重复的记录,是否有任何方法可以获得唯一的记录。@SidM我纠正了我的输入错误。让我知道这是否正确现在不,它仍然提供副本results@SidM好的,我想我已经修好了谢谢你的回答:)