SQL Server求解最近多少销售记录的销售额占比总销售额的指定比例

看园中SQL Server大V潇潇隐者的博文,发现一边文就是描述了如标题描述的问题

具体的问题描述我通过潇潇隐者的博文的截图来阐释:

注意:如果以上截取有所侵权,也请作者告知,再次感谢。

当看到这个问题的,我想到了是窗口函数提供的累积汇总有关的解决方案。

准备测试数据,有关的T-SQL代码如下:

 1 IF OBJECT_ID(N‘dbo.SalesData‘, N‘U‘) IS NOT NULL
 2 BEGIN
 3     DROP TABLE dbo.SalesData;
 4 END
 5 GO
 6
 7 CREATE TABLE dbo.SalesData
 8 (   
 9     Product_Name CHAR(32) NOT NULL, --商品名称   
10     Sale_Amount FLOAT NOT NULL   --销售金额
11 );
12 GO
13
14 INSERT INTO dbo.SalesData (Product_Name, Sale_Amount)
15 SELECT ‘ProductNameA‘, 13000 UNION ALL
16 SELECT ‘ProductNameA‘, 12000 UNION ALL
17 SELECT ‘ProductNameA‘, 9000 UNION ALL
18 SELECT ‘ProductNameB‘, 167000 UNION ALL
19 SELECT ‘ProductNameB‘, 137000 UNION ALL
20 SELECT ‘ProductNameB‘, 107000 UNION ALL
21 SELECT ‘ProductNameC‘, 78000 UNION ALL
22 SELECT ‘ProductNameC‘, 12000;
23 GO

执行以下的T-SQL代码:

1 SELECT Product_Name, Sale_Amount
2 FROM dbo.SalesData;
3 GO

得到的结果如下:

注意:以上测试数据也是来自潇潇隐者的博文,我再次基础上做了调整。

基于SQL Server 2005和以上的版本的解决方案的T-SQL代码如下:

 1 -- SQL Server 2005 和以上版本 使用子查询的解决方案
 2 SELECT *
 3 FROM (
 4     SELECT T.Product_Name, T.Sale_Amount, T.rownum, T.Sale_TotalAmount, T.Sale_AccumulateAmount
 5         ,100.0 * T.Sale_AccumulateAmount / T.Sale_TotalAmount AS Sale_AccumulatePercent
 6     FROM (
 7         SELECT T.Product_Name, T.Sale_Amount, ROW_NUMBER() OVER (ORDER BY T.Sale_Amount DESC) AS rownum, T2.Sale_TotalAmount
 8             ,(SELECT SUM(Sale_Amount) FROM dbo.SalesData WHERE Sale_Amount >= T.Sale_Amount) AS Sale_AccumulateAmount
 9         FROM dbo.SalesData AS T
10         CROSS APPLY (SELECT SUM(Sale_Amount) AS Sale_TotalAmount FROM dbo.SalesData) AS T2
11     ) AS T
12 ) AS T
13 WHERE T.Sale_AccumulatePercent <= 80;
14 GO
15  

执行后的查询结果如下:

基于SQL Server 2012和以上的版本的解决方案的T-SQL代码如下:

 1 -- SQL Server 2012 和以上 使用增强的窗口函数的解决方案
 2 SELECT T.Product_Name, T.Sale_Amount, T.rownum, T.Sale_TotalAmount, T.Sale_AccumulateAmount, T.Sale_AccumulatePercent
 3 FROM (
 4     SELECT T.Product_Name, T.Sale_Amount, T.rownum, T.Sale_TotalAmount, T.Sale_AccumulateAmount
 5     ,100.0 * T.Sale_AccumulateAmount / T.Sale_TotalAmount AS Sale_AccumulatePercent /*累计销售额在总销售中的百分比*/
 6     FROM (
 7         SELECT Product_Name, Sale_Amount, ROW_NUMBER() OVER (ORDER BY Sale_Amount DESC) AS rownum /*行号行数,具有不确定性,窗口排序字句列不唯一*/
 8         ,SUM(Sale_Amount) OVER () AS Sale_TotalAmount /*总销售额*/
 9         ,SUM(Sale_Amount) OVER (ORDER BY Sale_Amount DESC ROWS UNBOUNDED PRECEDING) AS Sale_AccumulateAmount /* 累计销售额,使用了SQL Server 2012窗口函数新增的窗口框架字句,也等同于 ROWS BETWEEN UNBOUNDED PRECEDING AND CURRENT ROW*/
10         FROM dbo.SalesData
11     ) AS T
12 ) AS T
13 WHERE T.Sale_AccumulatePercent <= 90;
14 GO

执行后的查询结果如下:

博友有其他的解决方案,也请不吝赐教,万分感谢。

时间: 2024-11-05 13:45:54

SQL Server求解最近多少销售记录的销售额占比总销售额的指定比例的相关文章

在SQL Server中快速删除重复记录

在SQL Server中快速删除重复记录 2006-07-17 21:53:15 分类: SQL Server 开发人员的噩梦——删除重复记录 想必每一位开发人员都有过类似的经历,在对数据库进行查询或统计的时候不时地会碰到由于表中存在重复的记录而导致查询和统计结果不准确.解决该问题的办法就是将这些重复的记录删除,只保留其中的一条. 在SQL Server中除了对拥有十几条记录的表进行人工删除外,实现删除重复记录一般都是写一段代码,用游标的方法一行一行检查,删除重复的记录.因为这种方法需要对整个表

SQL Server中遍历表中记录的方法

遍历表有下面几种方法 1.使用游标 2.使用表变量 3.使用临时表 下面通过一个实例分别介绍三中方法的实现: 1.需求 给HR.Employees表,fullname 列赋值,其值为 firstname+lastname 为了演示表的遍历,忽略 UPDATE HR.Employees SET fullname= firstname+' '+lastname; 的实现方式 2.使用游标 使用游标的代码主要有以下几个步骤,声明游标,打开游标,使用游标,关闭游标和释放游标. -- 方法1:游标 -- 

MS SQL Server数据恢复软件测试-导出结果记录数量对比

一. 测试目的:MS SQL Server数据恢复软件是一款恢复故障数据库的工具,其设计的目的是为了解决坏库的数据恢复.本工具最基本的恢复功能是正常情况下能恢复出任何好库的数据而不存在偏差,但在实际情况下,各种应用的数据库存在着不同的使用场景以及开发环境,有着细微差异,软件恢复要顾及到各种细节,难免会漏掉一些关键细节而导致恢复结果不一定能达到100%,所以数据库恢复测试比对能得出相应的改进办法,提高软件质量.二. 测试步骤:对一个好库的测试,我们在实际数据恢复业务中,会接触到各种各样的应用数据库

SQL Server使用sp_spaceused查看表记录存在不准确的情况

  在之前写过一篇博客"关系数据库如何快速查询表的记录数",里面介绍了使用sp_spaceused查看表的记录数是否正确的问题,具体如下: 关于问题3:有多个索引的表,是否记录数会存在不一致的情况? 答案:个人测试以及统计来看,暂时发现多个索引的情况下,sys.partitions中的rows记录数都是一致的.暂时没有发现不一致的情况,当然也不排除有特殊情况. 关于问题5: 分区表的情况又是怎么样? 答案:分区表和普通表没有任何区别. 关于问题6:对象目录视图sys.partition

SQL Server 2008 R2——开发后记录

==================================声明================================== 本文原创,转载在正文中显要的注明作者和出处,并保证文章的完整性. 未经作者同意请勿修改(包括本声明),保留法律追究的权利. 未经作者同意请勿用于出版.印刷或学术引用. 本文不定期修正完善,为保证内容正确,建议移步原文处阅读. 本文链接:http://www.cnblogs.com/wlsandwho/p/4337626.html =============

SQL Server Update 根据自身表不同记录的值修改,链表修改

一.自链接方式 update b1 set b1.money = b1.money + b2.money from (select * from wallet where type='余额') b1 inner join (select * from wallet where type='积分') b2 on b1.userId= b2.userId 二.表链接 update r set r.cEnable = 0 from 表1 r inner join 表2 t on t.cId = r.c

Sql Server中清空所有数据表中的记录

清空所有数据表中的记录: 代码如下:exec sp_msforeachtable  @Command1 ='truncate table ?'删除所有数据表: 代码如下:exec sp_msforeachtable 'delete   N''?'''清空SQL Server数据库中所有表数据的方法(有约束的情况) 其实删除数据库中数据的方法并不复杂,为什么我还要多此一举呢,一是我这里介绍的是删除数据库的所有数据,因为数据之间可能形成相互约束关系,删除操作可能陷入死循环,二是这里使用了微软未正式公

Sql Server删除数据表中重复记录 三种方法

本文介绍了Sql Server数据库中删除数据表中重复记录的方法. [项目]数据库中users表,包含u_name,u_pwd两个字段,其中u_name存在重复项,现在要实现把重复的项删除![分析]1.生成一张临时表new_users,表结构与users表一样:2.对users表按id做一个循环,每从users表中读出一个条记录,判断new_users中是否存在有相同的u_name,如果没有,则把它插入新表:如果已经有了相同的项,则忽略此条记录:3.把users表改为其它的名称,把new_use

(4.7)怎么捕获和记录SQL Server中发生的死锁?

转自:https://blog.csdn.net/c_enhui/article/details/19498327 怎么捕获和记录SQL Server中发生的死锁? sql server如何让错误日志记录死锁 2014年02月19日 18:25:55 阅读数:1313 我们知道,可以使用SQL Server自带的Profiler工具来跟踪死锁信息.但这种方式有一个很大的敝端,就是消耗很大.据国外某大神测试,profiler甚至可以占到服务器总带宽的35%,所以,在一个繁忙的系统中,使用profi