【问题标题】:Sorting Number Columns in Order In SSRS在SSRS中按顺序对数字列进行排序
【发布时间】:2016-10-27 20:56:15
【问题描述】:

我正在使用 Microsoft SQL Server 2012 和 Visual Studio 2012。在我的 SQL 代码中,我开发了一个 AgeBucket 列,它基本上将计算请求的开始日期和结束日期之间的天数。我的代码如下(我提前为它的长代码道歉。)

它有效,当我尝试将其带入我的 SSRS 报告的数据集时,它也有效,但是对于列,数字出现乱序。它显示 6-10 作为最后一列,并且在按 AgeBucket 分组时,所有其他列似乎都是按顺序排列的。我意识到 SSRS 可能正在查看每列的第一个数字,这就是为什么 6-10 排在最后的原因。

我的问题是,如何在 SSRS 中按顺序对这些数字进行排序?我的 ColumnGroups 中有 AgeBucket 列,但不确定排序以按顺序获取正确列中的信息的最佳方法。

         CASE WHEN 
            CASE WHEN A.[EndDate] > A.[StartDate] THEN C2.[BusinessCalendarDay] - C1.[BusinessCalendarDay]  
                 WHEN A.[EndDate] IS NULL and A.[StartDate] IS NOT NULL THEN C3.[BusinessCalendarDay] - C1.[BusinessCalendarDay]
                 WHEN A.[EndDate] = A.[StartDate] THEN 1
         END BETWEEN 0 AND 6
         THEN '0-5'
         WHEN 
            CASE WHEN A.[EndDate] > A.[StartDate] THEN C2.[BusinessCalendarDay] - C1.[BusinessCalendarDay]  
                 WHEN A.[EndDate] IS NULL and A.[StartDate] IS NOT NULL THEN C3.[BusinessCalendarDay] - C1.[BusinessCalendarDay]
                 WHEN A.[EndDate] = A.[StartDate] THEN 1
         END BETWEEN 6 AND 10
         THEN '6-10'
         WHEN
            CASE WHEN A.[EndDate] > A.[StartDate] THEN C2.[BusinessCalendarDay] - C1.[BusinessCalendarDay]  
                 WHEN A.[EndDate] IS NULL and A.[StartDate] IS NOT NULL THEN C3.[BusinessCalendarDay] - C1.[BusinessCalendarDay]
                 WHEN A.[EndDate] = A.[StartDate] THEN 1
         END BETWEEN 11 AND 15
         THEN '11-15'
         WHEN
            CASE WHEN A.[EndDate] > A.[StartDate] THEN C2.[BusinessCalendarDay] - C1.[BusinessCalendarDay]  
                 WHEN A.[EndDate] IS NULL and A.[StartDate] IS NOT NULL THEN C3.[BusinessCalendarDay] - C1.[BusinessCalendarDay]
                 WHEN A.[EndDate] = A.[StartDate] THEN 1
         END BETWEEN 16 AND 20
         THEN '16-20'
         WHEN
            CASE WHEN A.[EndDate] > A.[StartDate] THEN C2.[BusinessCalendarDay] - C1.[BusinessCalendarDay]  
                 WHEN A.[EndDate] IS NULL and A.[StartDate] IS NOT NULL THEN C3.[BusinessCalendarDay] - C1.[BusinessCalendarDay]
                 WHEN A.[EndDate] = A.[StartDate] THEN 1
         END BETWEEN 21 AND 25
         THEN '21-25'
         WHEN
            CASE WHEN A.[EndDate] > A.[StartDate] THEN C2.[BusinessCalendarDay] - C1.[BusinessCalendarDay]  
                 WHEN A.[EndDate] IS NULL and A.[StartDate] IS NOT NULL THEN C3.[BusinessCalendarDay] - C1.[BusinessCalendarDay]
                 WHEN A.[EndDate] = A.[StartDate] THEN 1
         END BETWEEN 26 AND 30
         THEN '26-30'
         WHEN
            CASE WHEN A.[EndDate] > A.[StartDate] THEN C2.[BusinessCalendarDay] - C1.[BusinessCalendarDay]  
                 WHEN A.[EndDate] IS NULL and A.[StartDate] IS NOT NULL THEN C3.[BusinessCalendarDay] - C1.[BusinessCalendarDay]
                 WHEN A.[EndDate] = A.[StartDate] THEN 1
         END BETWEEN 31 AND 35
         THEN '31-35'
         WHEN
            CASE WHEN A.[EndDate] > A.[StartDate] THEN C2.[BusinessCalendarDay] - C1.[BusinessCalendarDay]  
                 WHEN A.[EndDate] IS NULL and A.[StartDate] IS NOT NULL THEN C3.[BusinessCalendarDay] - C1.[BusinessCalendarDay]
                 WHEN A.[EndDate] = A.[StartDate] THEN 1
         END BETWEEN 35 AND 40
         THEN '35-40'
         WHEN
            CASE WHEN A.[EndDate] > A.[StartDate] THEN C2.[BusinessCalendarDay] - C1.[BusinessCalendarDay]  
                 WHEN A.[EndDate] IS NULL and A.[StartDate] IS NOT NULL THEN C3.[BusinessCalendarDay] - C1.[BusinessCalendarDay]
                 WHEN A.[EndDate] = A.[StartDate] THEN 1
         END > 40
         THEN '41+'
    END AS AgeBucket
    FROM CAST(A.StartDate AS DATE) = C1.[CAL_DT]        
    LEFT JOIN [dbo].[DT_DIM] AS C2 
    ON CAST(A.EndDate AS DATE) = C2.[CAL_DT]        
    LEFT JOIN [dbo].[DT_DIM] AS C3 
    ON CAST(GETDATE() AS DATE) = C3.[CAL_DT]

【问题讨论】:

  • 对我来说还不清楚你想要什么。只有一个正确的地方可以放置排序:最外面的SELECT。在您的最终ORDER BY 中,允许使用给定的别名。另一种方法是将完整查询包装为CTE 并执行SELECT * FROM CTE ORDER BY col1,col2,...。包装为子选择的查询也是如此。
  • 您的意思是 rows 出现故障而不是 columns 对吧?
  • 上面的代码只是更专注于解释我是如何创建我的 AgeBucket 字段的。我的主要目标是当我在 SSRS 中填充这个数据集字段时,当我按 AgeBucket 分组时它没有按顺序显示。它去了“0-5”、“11-15”、“16-20”……最后出现了“6-10”。但是检查的答案解释了如何修复它,需要在 SSRS 列组类别中轻松排序。
  • @Searching - 不,列乱序...不是行。

标签: sorting date reporting-services sql-server-2012 ssrs-2012


【解决方案1】:

你是对的 - 因为你的字段是一个文本字段,所以它是按第一个字符排序的。

我只想在您的 SSRS 组的 SORT 中使用 IIF 语句:

=IIF(Fields!AgeBucket.Value = "0-5",   1, 
 IIF(Fields!AgeBucket.Value = "6-10",  2, 
 IIF(Fields!AgeBucket.Value = "11-15", 3, 
 IIF(Fields!AgeBucket.Value = "16-20", 4, 
 IIF(Fields!AgeBucket.Value = "21-25", 5, 
 IIF(Fields!AgeBucket.Value = "26-30", 6, 
 IIF(Fields!AgeBucket.Value = "31-35", 7, 
 IIF(Fields!AgeBucket.Value = "36-40", 8, 
 IIF(Fields!AgeBucket.Value = "41+", 9, 10)

【讨论】:

  • 谢谢@Hannover,这很有效,这正是我使用 SSRS 所需要的。欣赏你!
【解决方案2】:

你有一些选择。

  1. 更改存储桶标签,以便它们按照您喜欢的方式排序。它们是文本,因此添加前导零可能是您想要做的。

'0-5' 需要是'00-05''6-10' -> '06-10' 等。不那么漂亮。

  1. 在查询中添加另一个字段,就像您为存储桶使用的字段一样,但使用数字而不是文本标签。使用这个新字段在报告中排序。

见下文。我已经处理了这种情况。

    CASE WHEN 
            CASE WHEN A.[EndDate] > A.[StartDate] THEN C2.[BusinessCalendarDay] - C1.[BusinessCalendarDay]  
                 WHEN A.[EndDate] IS NULL and A.[StartDate] IS NOT NULL THEN C3.[BusinessCalendarDay] - C1.[BusinessCalendarDay]
                 WHEN A.[EndDate] = A.[StartDate] THEN 1
         END BETWEEN 0 AND 6
         THEN 10
         WHEN 
            CASE WHEN A.[EndDate] > A.[StartDate] THEN C2.[BusinessCalendarDay] - C1.[BusinessCalendarDay]  
                 WHEN A.[EndDate] IS NULL and A.[StartDate] IS NOT NULL THEN C3.[BusinessCalendarDay] - C1.[BusinessCalendarDay]
                 WHEN A.[EndDate] = A.[StartDate] THEN 1
         END BETWEEN 6 AND 10
         THEN 20
         WHEN
            CASE WHEN A.[EndDate] > A.[StartDate] THEN C2.[BusinessCalendarDay] - C1.[BusinessCalendarDay]  
                 WHEN A.[EndDate] IS NULL and A.[StartDate] IS NOT NULL THEN C3.[BusinessCalendarDay] - C1.[BusinessCalendarDay]
                 WHEN A.[EndDate] = A.[StartDate] THEN 1
         END BETWEEN 11 AND 15
         THEN 30
         WHEN
            CASE WHEN A.[EndDate] > A.[StartDate] THEN C2.[BusinessCalendarDay] - C1.[BusinessCalendarDay]  
                 WHEN A.[EndDate] IS NULL and A.[StartDate] IS NOT NULL THEN C3.[BusinessCalendarDay] - C1.[BusinessCalendarDay]
                 WHEN A.[EndDate] = A.[StartDate] THEN 1
         END BETWEEN 16 AND 20
         THEN 40
         WHEN
            CASE WHEN A.[EndDate] > A.[StartDate] THEN C2.[BusinessCalendarDay] - C1.[BusinessCalendarDay]  
                 WHEN A.[EndDate] IS NULL and A.[StartDate] IS NOT NULL THEN C3.[BusinessCalendarDay] - C1.[BusinessCalendarDay]
                 WHEN A.[EndDate] = A.[StartDate] THEN 1
         END BETWEEN 21 AND 25
         THEN 50
         WHEN
            CASE WHEN A.[EndDate] > A.[StartDate] THEN C2.[BusinessCalendarDay] - C1.[BusinessCalendarDay]  
                 WHEN A.[EndDate] IS NULL and A.[StartDate] IS NOT NULL THEN C3.[BusinessCalendarDay] - C1.[BusinessCalendarDay]
                 WHEN A.[EndDate] = A.[StartDate] THEN 1
         END BETWEEN 26 AND 30
         THEN 60
         WHEN
            CASE WHEN A.[EndDate] > A.[StartDate] THEN C2.[BusinessCalendarDay] - C1.[BusinessCalendarDay]  
                 WHEN A.[EndDate] IS NULL and A.[StartDate] IS NOT NULL THEN C3.[BusinessCalendarDay] - C1.[BusinessCalendarDay]
                 WHEN A.[EndDate] = A.[StartDate] THEN 1
         END BETWEEN 31 AND 35
         THEN 70
         WHEN
            CASE WHEN A.[EndDate] > A.[StartDate] THEN C2.[BusinessCalendarDay] - C1.[BusinessCalendarDay]  
                 WHEN A.[EndDate] IS NULL and A.[StartDate] IS NOT NULL THEN C3.[BusinessCalendarDay] - C1.[BusinessCalendarDay]
                 WHEN A.[EndDate] = A.[StartDate] THEN 1
         END BETWEEN 35 AND 40
         THEN 80
         WHEN
            CASE WHEN A.[EndDate] > A.[StartDate] THEN C2.[BusinessCalendarDay] - C1.[BusinessCalendarDay]  
                 WHEN A.[EndDate] IS NULL and A.[StartDate] IS NOT NULL THEN C3.[BusinessCalendarDay] - C1.[BusinessCalendarDay]
                 WHEN A.[EndDate] = A.[StartDate] THEN 1
         END > 40
         THEN 100
    END AS OrderBy

使用新的 OrderBy 列在 RDL 中排序。

  1. 将当前查询包装在SELECT 语句中,并通过评估AgeBucket 的值并设置正确的排序顺序来添加新列进行排序。使用新列在 RDL 中进行排序,如上所示。

见下文。

SELECT AA.*, CASE WHEN AA.AgeBucket = '0-5' THEN 10
WHEN AA.AgeBucket = '6-10' THEN 20
...
ELSE 100 END AS OrderBy
FROM (SELECT ...,
CASE WHEN 
    CASE WHEN A.[EndDate] > A.[StartDate] THEN C2.[BusinessCalendarDay] - C1.[BusinessCalendarDay]  
            WHEN A.[EndDate] IS NULL and A.[StartDate] IS NOT NULL THEN C3.[BusinessCalendarDay] - C1.[BusinessCalendarDay]
            WHEN A.[EndDate] = A.[StartDate] THEN 1
    END BETWEEN 0 AND 6
    THEN '0-5'
    WHEN 
    CASE WHEN A.[EndDate] > A.[StartDate] THEN C2.[BusinessCalendarDay] - C1.[BusinessCalendarDay]  
            WHEN A.[EndDate] IS NULL and A.[StartDate] IS NOT NULL THEN C3.[BusinessCalendarDay] - C1.[BusinessCalendarDay]
            WHEN A.[EndDate] = A.[StartDate] THEN 1
    END BETWEEN 6 AND 10
    THEN '6-10'
    ...
    THEN '41+'
END AS AgeBucket
...) AA -- End of wrapping SELECT

祝你好运!

【讨论】:

  • 虽然所有 3 种解决方案都有效,但在我的情况下,#1 和 #2 不一定有用。 #3确实有效,感谢您帮助我回答。只检查了上述一个作为答案,因为它允许我在 SSRS 中简单地排序,而无需操作原始 SQL 代码。但谢谢你,我感谢你的帮助!
  • 答案是一个很好的解决方案。我更倾向于首先更改 SQL,因为我更像是一名数据库管理员。如果存储桶需要更改,我想这一切都归结为您想要更改的位置...... RDL 或 SQL/存储过程。很高兴为您提供帮助!
猜你喜欢
  • 2020-09-29
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2023-04-01
  • 1970-01-01
  • 1970-01-01
  • 2013-05-02
相关资源
最近更新 更多