【发布时间】:2014-08-28 05:38:25
【问题描述】:
我对 R 比较陌生,所以我可能忽略了 R 中已经存在的函数。我已经使用循环创建了一个解决方案,但我想知道是否有 R 方法可以做到这一点(到目前为止,所有我的 R 脚本中的一部分是无循环的,因为它们应该是这样的!)
数据包含一个事件的 CSV 记录。该事件具有 ISO-8601 时间戳、响应时间和响应代码(指示成功或特定失败)。我可以将此 CSV 转换为数据框,并从时间戳字符串创建一个 R 日期和时间字段。目前没问题。
然后我确定一个固定长度的时间间隔的大小,用于分析和绘图。例如,假设 5 分钟。在前 5 分钟的时间间隔内,可能有 151 个事件(数据框中的行)。在接下来的 5 分钟间隔内,可能只有 130 个事件。等等。换句话说,正在分析其日志的客户端具有不均匀的请求负载和不同的请求率。我需要做的是每 5 分钟的时间间隔,然后为该窗口内的所有事件计算平均值、最大值、第 95 个百分位数和第 99 个百分位数。
这目前工作得很好,但我已经在 for 循环中实现了它。结果是需要相当长的时间:在 i7 CPU 上超过 5 秒)分析 18K 事件并将它们转换为 177 个 5 分钟间隔。对于相同的功能,这仍然比 Splunk 快。但似乎我应该使用现有的 R 函数。
例如,这里是我的“原始”数据框的头部(数据)。好吧,无论如何,几乎是原始的:如果需要,将行反转以确保行从最旧到最新排序,并且 event.datetime 列已添加 strptime 应用于 X_time 列的结果:
DATA HEAD:
X_time CODE RTIME event.datetime
18867 2014-08-20T00:00:17.971+0000 0 0.144 2014-08-20 00:00:17
18866 2014-08-20T00:00:17.973+0000 0 0.146 2014-08-20 00:00:17
18865 2014-08-20T00:00:18.156+0000 0 0.328 2014-08-20 00:00:18
18864 2014-08-20T00:00:18.177+0000 0 0.349 2014-08-20 00:00:18
18863 2014-08-20T00:00:18.264+0000 2057 0.437 2014-08-20 00:00:18
18862 2014-08-20T00:00:18.294+0000 0 0.467 2014-08-20 00:00:18
通过 dput():
DPUT DATA HEAD:
structure(list(X_time = c("2014-08-20T00:00:17.971+0000", "2014-08-20T00:00:17.973+0000",
"2014-08-20T00:00:18.156+0000", "2014-08-20T00:00:18.177+0000",
"2014-08-20T00:00:18.264+0000", "2014-08-20T00:00:18.294+0000"
), CODE = c(0L, 0L, 0L, 0L, 0L, 0L), RTIME = c(0.144,
0.146, 0.328, 0.349, 0.437, 0.467), event.datetime = structure(c(1408492817.971,
1408492817.973, 1408492818.156, 1408492818.177, 1408492818.264,
1408492818.294), class = c("POSIXct", "POSIXt"), tzone = "UTC")), .Names = c("X_time",
"CODE", "RTIME", "event.datetime"), row.names = c(18867L,
18866L, 18865L, 18864L, 18863L, 18862L), class = "data.frame")
这里是统计数据的头部(stats.data),每 5 分钟时间间隔有一行包含该行的统计信息(包括对这些统计数据有贡献的原始数据行数的计数) )。在这种情况下,正在分析的原始数据中的 RTIME(响应时间,以秒为单位)列的最大值、平均值(平均值)、第 95 个百分位和第 99 个百分位:
STATS HEAD:
Start Count Max Avg Perc95 Perc99
1 2014-08-20 00:00:17 151 0.545 0.3369073 0.4650 0.50200
2 2014-08-20 00:05:23 130 0.487 0.3543385 0.4630 0.47913
3 2014-08-20 00:10:28 158 0.492 0.3340190 0.4520 0.48315
4 2014-08-20 00:15:33 143 0.515 0.3547133 0.4518 0.49222
5 2014-08-20 00:20:39 115 0.469 0.3311739 0.4453 0.45616
6 2014-08-20 00:25:41 157 0.454 0.3262420 0.4440 0.45200
通过 dput():
DPUT STATS HEAD:
structure(list(Start = structure(c(1408492817.971, 1408493123.391,
1408493428.267, 1408493733.976, 1408494039.253, 1408494341.597
), class = c("POSIXct", "POSIXt"), tzone = "UTC"), Count = c(151L,
130L, 158L, 143L, 115L, 157L), Max = c(0.545, 0.487, 0.492, 0.515,
0.469, 0.454), Avg = c(0.336907284768212, 0.354338461538462,
0.334018987341772, 0.354713286713287, 0.331173913043478, 0.326242038216561
), Perc95 = c(0.465, 0.463, 0.452, 0.4518, 0.4453, 0.444), Perc99 = c(0.502,
0.47913, 0.48315, 0.49222, 0.45616, 0.452)), .Names = c("Start",
"Count", "Max", "Avg", "Perc95", "Perc99"), row.names = c(NA,
6L), class = "data.frame")
我问的主要是因为这似乎是一个常见问题,并且我认为我无法找到内置的 R 解决方案是我在寻找方面的错,而不是 R 的实际缺乏。此外,包括反转行和将 ISO-8601 X_time 列转换为 R 日期/时间 event.datetime 列在内的所有其他处理都非常快,这是我将事件逐行收集到正确的固定 -宽度时间间隔,这是一个闪电般快速脚本的一个缺点。
【问题讨论】:
-
POSIXlt 对象有
cut.和seq.方法。如果您发布了dput(head(stats.data)),您将获得一个有效的示例。尝试从控制台输出重建此类对象是一个真正的 PITA。
标签: r