2

我有一个看起来像这样的数据库表,称为 Totals,我正在尝试选择每人每月的最大日期,以便我可以平均该人在几个月内的余额

 Date       Person     Balance
01-15-12       A        79
01-23-12       c        150
01-17-12       A        65
02-23-12       c        150
02-15-12       A        70
03-23-12       c        15
03-15-12       A        705
03-28-12       c        150
04-15-12       A        700
04-23-12       c        150

我将此表加入到一个名为 #bal 的临时表中,其中只包含像 ABC 等人这样的人所以每个月我只想要每个人每月的最大行数,以便我可以总结余额并找到平均余额每人的月份。

  create table #bal 
 (  
 person bigint,
 avgbal decimal,
 mxdate datetime

 )
  insert into #bal(person,avgbal,mxdate)
  select 
  b.person,
  (sum(s.BAL)/12) as avgbal,
  max(date) as mxdate 

  from #bal b
  inner join TOTALS s on (b.person=s.person)
  where DATE between '01-17-2012' and getdate()
  group by b.person

到目前为止,有这样的东西按日期分组,但我只想选择每月的最大天数。

4

4 回答 4

2

我根据上面的集合创建的一些样本数据制作了几个样本。我不确定您是想要每个月的最后一个值还是最大值,因为它们不一定相同,所以我为两者编写了基本查询:

declare @table table
(
date date,
person varchar(10),
balance int
)

insert into @table
select '01-15-12', 'A', 79
union all
select '01-23-12', 'c', 150
union all
select '01-17-12', 'A', 65
union all
select '02-23-12', 'c', 150
union all
select '02-15-12', 'A', 70
union all
select '03-23-12', 'c', 15
union all
select '03-15-12', 'A', 705
union all
select '03-28-12', 'c', 150
union all
select '04-15-12', 'A', 700
union all
select '04-23-12', 'c', 150;

-- Average of max balance in month
with maxMonth as
(
  select year = year(date)
    , month = month(date)
    , person, monthMaxBalanace = max(balance)
  from @table
  where date between '01-17-2012' and getdate()
  group by year(date), month(date), person
)
select person, maxInMonthAverage = avg(monthMaxBalanace)
from maxMonth
group by person;

或者,如果您需要使用每个月的最后余额,您可以更改查询:

-- Average of last balance in month
with lastInMonth as
(
  select year = year(date)
    , month = month(date)
    , person, balance
    , monthRank = row_number() over (partition by year(date), month(date), person order by date desc)
  from @table
  where date between '01-17-2012' and getdate()
),
lastRows as
(
  select * from lastInMonth where monthRank = 1
)
select person, lastInMonthAverage = avg(balance)
from lastRows
group by person;

根据您的示例查询(即 1 月 17 日和更大),结果是相同的,但如果您包含 15 日的值,由于两个查询中的逻辑不同,它们会略有不同。

在此处输入图像描述

于 2013-01-23T13:58:05.063 回答
1

这将为您检索每个月和每个人的最后一天的行..

select V.[date]
  ,V.person
  ,V.balance
from (  select [person]
          ,[date]
          ,max([date]) over(partition by person,datediff(mm,0,[date])) as [max_date]
          ,balance
    from @table
)V
where V.[date]=V.max_date

这会为您检索期间所有月份的平均值

select V.person
,SUM(balance)/12 as avgbal_as_u_calc
,AVG(balance) as average_balance
from (  select [person]
          ,[date]
          ,max([date]) over(partition by person,datediff(mm,0,[date])) as [max_date]
          ,balance
    from @table
)V
where V.[date]=V.max_date
group by V.person
于 2013-01-23T15:28:16.427 回答
0

你在寻找这样的东西吗?查询可以被取消分组以显示每月数据。这里我对每个用户每个月的每个最大日期进行平衡,总结并给出年度平均值。

询问:

select x.person, sum(p.balance) maxtotal,
sum(p.balance) /12 average
from (select max(date) mxdt,
      month(Date) as month,
      person
from person
group by month(Date), person) x
join person p
on p.person = x.person
and p.date = x.mxdt
group by x.person;

| PERSON | MAXTOTAL | AVERAGE |
-------------------------------
|      A |     1540 |     128 |
|      c |      600 |      50 |
于 2013-01-23T13:58:45.707 回答
-2

这是 Oracle 查询。它不是基于你的表。可以这么说,所有数据都是即时的。内部查询将按月号为您提供日期,例如 01、02... 如果这是您想要的并且我正确理解了这个问题,则外部查询每月获得 MAX 值。您只需将日期转换为月份编号并按其分组。您可以将人员添加到分组依据。我希望这有帮助:

SELECT curr_mo, MAX(some_val) 
  FROM
   (-- 10 weeks starting with '01-15-2012' --
     SELECT to_char(to_date('01-15-2012', 'mm-dd-yyyy')+LEVEL*7, 'mm') curr_mo 
      , MOD(LEVEL, 2)+3 some_val
       FROM dual
     CONNECT BY LEVEL <= 10 
   )
  GROUP BY curr_mo
 /

 Inner query output:

 CURR_MO    SOME_VAL
 -------------------
  01         4
  01         3
  02         4
  02         3
  .....

  Output - MAX per each mo:

  CURR_MO   MAX(SOME_VAL)
  ------------------------
  01         4
  02         4
  03         4
  ....
于 2013-01-23T14:18:29.550 回答