来自CDR的同时通话
当每个事件只有开始时间和持续时间时,我需要对同时发生的事件进行分析。
细节
我有一个标准的CDR通话详细记录,其中包括:
- 通话日期(每次通话开始的时间
- 持续时间(整数,通话持续时间的秒数)
- 频道(字符串)
我需要提出的是在给定的时间段内每秒进行某种同时调用的分析。例如,我们昨天有同时通话的图表。
(问题是相同的,如果我们在网站上保留了访问者的日志,并且持续时间很长,希望同时获得一组网页的客户)
算法是什么?
我可以遍历给定时间段内的记录,并填充一个数组,该数组的每个存储桶对应于整个时间段内的1秒。这可行并且似乎很快,但是如果时间周期很大(例如..1年),则需要大量内存(3600x24x365x4字节〜120MB aprox)。
这是用于基于Web的交互式应用程序,因此我的内存占用空间应该足够小。
编辑
同时,我的意思是所有呼叫都在给定的秒数上进行。第二个是我的最小单位。我不能使用更大的值(例如一个小时),因为一个小时内的所有通话都不必同时保持。
解决方案
回答
我会在数据库上实现这一点。在DATEPART中使用GROUP BY子句,我们可以获取想要的任何时间段的同时调用的列表,以秒,分钟,小时为单位。
在Web端,我们只需要显示查询返回的直方图。
回答
@ eric-z-beard:我真的很希望能够在数据库上实现这一点。我喜欢建议,尽管它似乎可以带来一些好处,但我不太完全理解。你能详细说明吗?请回想一下,每个呼叫将持续几秒钟,并且每一秒都需要计数。如果使用DATEPART(或者MySQL上类似的东西),那么GROUP BY应该使用秒。参见关于同时记录的说明。
对此进行详细说明,我找到了一种使用临时表解决此问题的方法。假设温度保持从tStart到tEnd的所有秒数,我可以
SELECT temp.second, count(call.id) FROM call, temp WHERE temp.second between (call.start and call.start + call.duration) GROUP BY temp.second
然后,按照建议,Web应用程序应将其用作直方图。
回答
我们可以将静态Numbers表用于许多此类SQL技巧。 Numbers表仅包含0到n的整数,例如10000。
然后,临时表永远不需要创建,而是一个子查询,例如:
SELECT StartTime + Numbers.Number AS Second FROM Numbers
回答
我们可以使用3个字段创建表"'simultaneous_calls'":
yyyymmdd Char(8), day_second Number, -- second of the day, count Number -- count of simultaneous calls
Web服务可以从此表中获取"计数"值并进行一些统计。
Simultaneous_calls表将由某些批处理程序填充,这些程序将在每天结束后每天启动。
假设我们使用Oracle,该批处理可能会启动执行以下操作的PL / SQL过程:
- 在一天中的每一秒追加带有24 * 3600 = 86400条记录的表,默认的"计数"值= 0。
- 定义查询的" day_cdrs"游标:
Select to_char(calldate, 'yyyymmdd') yyyymmdd, (calldate - trunc(calldate)) * 24 * 3600 starting_second, duration duration From cdrs Where cdrs.calldate >= Trunc(Sysdate -1) And cdrs.calldate Iterates the cursor to increment 'count' field for the seconds of the call: For cdr in day_cdrs Loop Update simultaneos_calls Set count = count + 1 Where yyyymmdd = cdr.yyyymmdd And day_second Between cdr.starting_second And cdr.starting_second + cdr.duration; End Loop;