【问题标题】:How to sum up the data for the overlapped data in postgresql?postgresql中重叠数据如何汇总?
【发布时间】:2017-08-17 13:31:21
【问题描述】:

我有如下数据:

t_id s_id   date_1      date_2      T_count            expected Result
N1  1-1I    2012-12-11  2013-01-22  0.21327014218009478622 4.7
N2  1-1I    2011-08-03  2011-11-10  3.8461538461538462     4.7
N3  1-1I    2013-12-05  2013-12-20  1.6935483870967742     4.7
N4  1-1I    2014-12-08  2015-06-25  4.7727272727272727     4.7
N5  1-1I    2017-03-08  (null)      (null)                 4.7
N6  1-I6    2013-04-11  2013-10-03  0.61538461538461538462 0.97
N7  1-I6    2011-09-27  2013-06-20  0.37325038880248833651 0.97

如果相同 s_id 的 date1 和 date2 与不同 t_id 的相同 s_id 重叠,我想计算 t_count 值的总和,否则返回相同 s_id 的最大值。

现在我使用的 postgres 代码正在对值进行求和,而不考虑重叠,请您提出建议。

对于给定的 s_id,可能存在一些数据重叠而另一些不重叠的情况,因此对于重叠的年份,我们需要增加一些数据并找到所有案例中的最大值,例如个人、重叠并给出一个答案是最大的。

select t1.s_id,sum(t1.t_count) 
              from abc t1
              JOIN abc t2
              ON daterange(t1.date_1, t1.date_2, '[]')
                             && daterange(t1.date_1, t1.date_2, '[]')
                                      and t1.s_id = t2.s_id
              GROUP BY t1.s_id

【问题讨论】:

  • 您应该仅加入 s_id 并检查 case when 中是否重叠 - 但我不明白为什么您只在 t1 日期上构建日期范围 - 什么应该与什么重叠?.. 或者它只是一个错字? ..
  • 如果某个s_id 的某些间隔只有重叠,结果应该是什么?例如,如果将N3date_1 更改为2013-01-05,结果会是什么?
  • 你是如何得到预期结果的1.970.62 + 0.370.99
  • @vladimir:我的错..我在创建示例数据,所以错误地做了那一点

标签: sql postgresql overlap date-range


【解决方案1】:

如果某个s_id 的某些间隔重叠而某些不重叠,则不清楚逻辑应该如何工作。

如果您知道数据中的所有区间都重叠,或者没有重叠,那么很容易确定它。

计算每个间隔的持续时间并总结所有这些持续时间。将其与从第一个日期到最后一个日期的持续时间进行比较。

我认为date_2 中的NULL 表示未来某个非常大的日期。

WITH
CTE
AS
(
    SELECT
        s_id
        ,SUM(COALESCE(date_2, '9999-12-31') - date_1) AS TotalDuration
        ,MIN(date_1) AS FirstDate
        ,MAX(COALESCE(date_2, '9999-12-31')) AS LastDate
        ,SUM(T_count) AS SumCount
        ,MAX(T_count) AS MaxCount
    FROM YourTable
    GROUP BY s_id
)
SELECT
    s_id
    ,CASE WHEN TotalDuration > (LastDate - FirstDate)
    THEN -- intervals overlap
        SumCount
    ELSE -- none of the intervals overlap
        MaxCount
    END AS Result
FROM CTE
;

【讨论】:

    【解决方案2】:

    我在与自己比较时犯了错误,我稍微修改了代码以获得这个结果。

    with cte as
    (
    
        select t1.s_id,sum(t1.t_count) as scount
                      from abc t1
                      JOIN abc t2
                      ON daterange(t1.date_1, t1.date_2, '[]')
                                     && daterange(t1.date_1, t1.date_2, '[]')
                                              and t1.s_id = t2.s_id
                      and t1.s_id ! = t2.s_id
                      GROUP BY t1.s_id
    ) 
    select 
          s_id,greatest(scount,max(t_count) over (partition by s_id)) as finalvalue 
    from abc 
    left outer join cte 
    on abc.s_id = cte.s_id
    

    【讨论】:

      猜你喜欢
      • 2017-12-06
      • 2011-12-05
      • 1970-01-01
      • 2019-08-29
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多