我得到了一份我需要提出的报告,这让我有些头痛,只是希望你们中的一个能帮助我。
我本来会创建一个SQLFiddle,但它现在给出了一些问题,它一直给我这个错误
发生未知错误:XML文档结构必须在同一实体中开始和结束:
这是我得到的样本数据
CREATE TABLE ActivityStatisticsPerWeek
([Client_Id] varchar(10), [Project_Id] varchar(4), [Activity_Group] int, [Activity_Id] int, [Activity_Name] varchar(56), [Total_Booked] int, [Price_Including_VAT] int, [Total] int, [WeekStart] datetime, [Use_For_Statistics] int, [Statistics_Group_Id] int, [Description] varchar(27))
;
INSERT INTO ActivityStatisticsPerWeek
([Client_Id], [Project_Id], [Activity_Group], [Activity_Id], [Activity_Name], [Total_Booked], [Price_Including_VAT], [Total], [WeekStart], [Use_For_Statistics], [Statistics_Group_Id], [Description])
VALUES
('CLIENT', 'TEST', 1000, 1005, 'Complimentary registration for Full Congress promo code)', 1, 0, 0, '2015-02-09', 1, 8, 'Complimentary Registrations'),
('CLIENT', 'TEST', 1000, 1005, 'Complimentary registration for Full Congress promo code)', 1, 0, 0, '2015-09-28', 1, 8, 'Complimentary Registrations'),
('CLIENT', 'TEST', 2000, 2500, 'BSI Member EARLY attending 01 December', 1, 160, 160, '2014-10-27', 1, 9, 'Full Registrations'),
('CLIENT', 'TEST', 2000, 2500, 'BSI Member EARLY attending 01 December', 1, 160, 160, '2015-02-09', 1, 9, 'Full Registrations'),
('CLIENT', 'TEST', 2000, 2500, 'BSI Member EARLY attending 01 December', 1, 160, 160, '2015-02-16', 1, 9, 'Full Registrations'),
('CLIENT', 'TEST', 2000, 2510, 'BSI Member EARLY attending 02 December', 1, 160, 160, '2015-02-09', 1, 9, 'Full Registrations'),
('CLIENT', 'TEST', 2000, 2520, 'BSI Member EARLY attending 03 December', 1, 160, 160, '2015-02-09', 1, 9, 'Full Registrations'),
('CLIENT', 'TEST', 2000, 2530, 'BSI Member EARLY attending 04 December', 1, 160, 160, '2015-02-09', 1, 9, 'Full Registrations')
;
如果您运行SELECT *,数据将以此格式显示
Client_Id|Project_Id|Activity_Group|Activity_Id|Activity_Name |Total_Booked|Price_Including_VAT|Total |WeekStart |Use_For_Statistics|Statistics_Group_Id|Description |
---------|----------|--------------|-----------|--------------------------------------------------------|------------|-------------------|------|-----------|------------------|-------------------|---------------------------|
CLIENT |TEST |1000 |1005 |Complimentary registration for Full Congress promo code)|1 |0.00 |0.00 |Feb 9 2015|1 |8 |Complimentary Registrations|
CLIENT |TEST |1000 |1005 |Complimentary registration for Full Congress promo code)|1 |0.00 |0.00 |Sep 28 2015|1 |8 |Complimentary Registrations|
CLIENT |TEST |2000 |2500 |Member EARLY attending 01 December |1 |160.00 |160.00|Oct 27 2014|1 |9 |Full Registrations |
CLIENT |TEST |2000 |2500 |Member EARLY attending 01 December |1 |160.00 |160.00|Feb 9 2015|1 |9 |Full Registrations |
CLIENT |TEST |2000 |2500 |Member EARLY attending 01 December |1 |160.00 |160.00|Feb 16 2015|1 |9 |Full Registrations |
CLIENT |TEST |2000 |2510 |Member EARLY attending 02 December |1 |160.00 |160.00|Feb 9 2015|1 |9 |Full Registrations |
CLIENT |TEST |2000 |2520 |Member EARLY attending 03 December |1 |160.00 |160.00|Feb 9 2015|1 |9 |Full Registrations |
CLIENT |TEST |2000 |2530 |Member EARLY attending 04 December |1 |160.00 |160.00|Feb 9 2015|1 |9 |Full Registrations |
我需要这样的数据。不要担心颜色或格式,图像只是客户提供的样本。
我一直在尝试使用存储过程来动态转动列,到目前为止这是我已经得到的代码
USE [EventLogic]
GO
/****** Object: StoredProcedure [dbo].[usp_RptActivityStatisticsPerWeek_InColumns] Script Date: 02/26/2015 13:45:26 ******/
SET ANSI_NULLS ON
GO
SET QUOTED_IDENTIFIER ON
GO
-- =============================================
-- Author: <Author,,Name>
-- Create date: <Create Date,,>
-- Description: <Description,,>
-- =============================================
CREATE PROCEDURE [dbo].[usp_RptActivityStatisticsPerWeek_InColumns] ( @Client_Id nvarchar(50), @Project_Id nvarchar(50))
AS
BEGIN
-- SET NOCOUNT ON added to prevent extra result sets from
-- interfering with SELECT statements.
SET NOCOUNT ON;
-- Insert statements for procedure here
DECLARE @colsPivot AS NVARCHAR(MAX),
@query AS NVARCHAR(MAX)
select @colsPivot = STUFF((SELECT ',' + QUOTENAME(c.col + '_'+ CONVERT(varchar(11), WeekStart, 109))
from [uvw_RptActivityStatisticsPerWeek]
cross apply
(
SELECT 'Total_Booked' col, 1 so union all
SELECT 'Price_Including_VAT', 2 se UNION ALL
SELECT 'Total', 3
) c
WHERE uvw_RptActivityStatisticsPerWeek.Client_Id = @Client_Id AND uvw_RptActivityStatisticsPerWeek.Project_Id = @Project_Id AND uvw_RptActivityStatisticsPerWeek.WeekStart IS NOT NULL
group by col, WeekStart, so
order by WeekStart, so
FOR XML PATH(''), TYPE
).value('.', 'NVARCHAR(MAX)')
,1,1,'')
set @query =
'select
Client_id,
Project_id,
Statistics_Group_Id,
Description,
Activity_Id,
Activity_Name,
'+@colsPivot+'
FROM
(
SELECT
app.Client_Id,
app.Project_Id,
a.Activity_Group,
a.Activity_Id,
a.Activity_Name,
SUM(app.Number_Of_Persons) AS [Total_Booked],
CAST(a.Price_Including_VAT/100 AS money) AS [Price_Including_VAT],
CAST((SUM(app.Number_Of_Persons) * (a.Price_Including_VAT /100)) AS money) AS [Total],
CONVERT(varchar(11), CAST(DATEADD(week, DATEDIFF(week, 0, p.Date_Confirmed), 0) AS date), 109) AS WeekStart,
a.Use_For_Statistics,
a.Statistics_Group_Id,
asg.Description
FROM dbo.ActivitiesPerPerson app
INNER JOIN dbo.Activities a ON a.Client_Id = app.Client_Id AND a.Project_Id = app.Project_Id AND a.Activity_Id = app.Activity_Id AND a.Use_For_Statistics = 1
INNER JOIN uvw_Participants p ON p.Client_Id = app.Client_Id AND p.Project_Id = app.Project_Id AND p.Person_Id = app.Person_Id AND p.Balance = 0 AND p.Date_Registered IS NOT NULL
INNER JOIN dbo.ActivityStatisticsGroups asg ON asg.Client_Id = a.Client_Id AND asg.Project_Id = a.Project_Id AND asg.Id = a.Statistics_Group_Id
GROUP BY
app.Client_Id,
app.Project_Id,
a.Activity_Group,
a.Activity_Id,
a.Activity_Name,
(app.Number_Of_Persons),
a.Price_Including_VAT,
(app.Number_Of_Persons * a.Price_Including_VAT),
DATEADD(week, DATEDIFF(week, 0, p.Date_Confirmed), 0),
a.Use_For_Statistics,
a.Statistics_Group_Id,
asg.Description
) p
PIVOT
(
MIN(Activity_Id)
FOR Total_Booked IN (' + @colsPivot + ')
) AS Dest
Where Client_Id=''' + @Client_Id + ''' AND Project_Id=''' + @Project_Id + ''''
PRINT(@query)
exec(@query)
END
GO
这是生成的查询
select
Client_id,
Project_id,
Statistics_Group_Id,
Description,
Activity_Id,
Activity_Name,
[Total_Booked_Feb 9 2015],[Price_Including_VAT_Feb 9 2015],[Total_Feb 9 2015],[Total_Booked_Feb 16 2015],[Price_Including_VAT_Feb 16 2015],[Total_Feb 16 2015],[Total_Booked_Oct 27 2014],[Price_Including_VAT_Oct 27 2014],[Total_Oct 27 2014],[Total_Booked_Sep 28 2015],[Price_Including_VAT_Sep 28 2015],[Total_Sep 28 2015]
FROM
(
SELECT
app.Client_Id,
app.Project_Id,
a.Activity_Group,
a.Activity_Id,
a.Activity_Name,
SUM(app.Number_Of_Persons) AS [Total_Booked],
CAST(a.Price_Including_VAT/100 AS money) AS [Price_Including_VAT],
CAST((SUM(app.Number_Of_Persons) * (a.Price_Including_VAT /100)) AS money) AS [Total],
CONVERT(varchar(11), CAST(DATEADD(week, DATEDIFF(week, 0, p.Date_Confirmed), 0) AS date), 109) AS WeekStart,
a.Use_For_Statistics,
a.Statistics_Group_Id,
asg.Description
FROM dbo.ActivitiesPerPerson app
INNER JOIN dbo.Activities a ON a.Client_Id = app.Client_Id AND a.Project_Id = app.Project_Id AND a.Activity_Id = app.Activity_Id AND a.Use_For_Statistics = 1
INNER JOIN uvw_Participants p ON p.Client_Id = app.Client_Id AND p.Project_Id = app.Project_Id AND p.Person_Id = app.Person_Id AND p.Balance = 0 AND p.Date_Registered IS NOT NULL
INNER JOIN dbo.ActivityStatisticsGroups asg ON asg.Client_Id = a.Client_Id AND asg.Project_Id = a.Project_Id AND asg.Id = a.Statistics_Group_Id
GROUP BY
app.Client_Id,
app.Project_Id,
a.Activity_Group,
a.Activity_Id,
a.Activity_Name,
(app.Number_Of_Persons),
a.Price_Including_VAT,
(app.Number_Of_Persons * a.Price_Including_VAT),
DATEADD(week, DATEDIFF(week, 0, p.Date_Confirmed), 0),
a.Use_For_Statistics,
a.Statistics_Group_Id,
asg.Description
) p
PIVOT
(
MIN(Total_Booked)
FOR Total_Booked IN ([Total_Booked_Feb 9 2015],[Price_Including_VAT_Feb 9 2015],[Total_Feb 9 2015],[Total_Booked_Feb 16 2015],[Price_Including_VAT_Feb 16 2015],[Total_Feb 16 2015],[Total_Booked_Oct 27 2014],[Price_Including_VAT_Oct 27 2014],[Total_Oct 27 2014],[Total_Booked_Sep 28 2015],[Price_Including_VAT_Sep 28 2015],[Total_Sep 28 2015])
) AS Dest
Where Client_Id='CLIENT' AND Project_Id='TEST'
但它给了我这个错误
Msg 8114, Level 16, State 1, Line 45
Error converting data type nvarchar to int.
Msg 473, Level 16, State 1, Line 45
The incorrect value "Total_Booked_Feb 9 2015" is supplied in the PIVOT operator.
任何帮助都会很棒!
谢谢
答案 0 :(得分:0)
我的小评论确实回答了为什么你得到了你得到的错误,但并没有完全涵盖你的问题:如何转动3列。简而言之,首先将值取消转换为单个列,然后将值转回。以下示例是生成的查询应如下所示的简化版本:
WITH Data AS (
SELECT *
FROM (VALUES
('Group A', '1 Jan',12,12,12)
, ('Group A', '1 Jan',12,12,12)
, ('Group A', '1 Feb',12,12,12)
, ('Group A', '1 Feb',12,12,12)
, ('Group B', '1 Jan',12,12,12)
, ('Group B', '1 Jan',12,12,12)
, ('Group B', '1 Feb',12,12,12)
, ('Group B', '1 Feb',12,12,12)
) AS T([Group], [Date], ValA, ValB, ValC)
),
Unpvt AS (
SELECT [Group]
, ColumnName = UPVT.ValName + ' ' + UPVT.Date
, ColumnValue = UPVT.Val
FROM Data
UNPIVOT (Val FOR ValName IN (ValA, ValB, ValC)) AS UPVT
)
SELECT * FROM Unpvt
PIVOT (
SUM(ColumnValue)
FOR ColumnName
IN ( [ValA 1 Jan]
, [ValB 1 Jan]
, [ValC 1 Jan]
, [ValA 1 Feb]
, [ValB 1 Feb]
, [ValC 1 Feb]
)) AS PVT