如何计算数据框中日期时间列的两个或多个类别的时间
How to calculate the time for two or more category for datetime column in dataframe
我有一个由日期时间、class 列组成的数据框。 class 列的值为 'open'、'close'。这是一个物联网数据。我必须计算总开放时间和总关闭时间。数据框是-
index datetime class
------------------------------------------
0 2020-10-05 08:55:00.161326 open
1 2020-10-05 09:00:00.137587 close
2 2020-10-05 09:05:00.089382 close
3 2020-10-05 09:10:00.219278 close
4 2020-10-05 09:15:00.160964 close
5 2020-10-06 09:20:00.315548 close
6 2020-10-06 09:25:00.080932 open
7 2020-10-06 09:30:00.335536 open
8 2020-10-06 09:35:00.202047 close
9 2020-10-06 09:45:00.242022 open
我需要得到的回应是-
index day_count hour_count class
-----------------------------------------------
0 0 0:15:00.097376 open
1 1 23:59:59.918860 close
基本上我正在尝试使用数据捕获传感器的运行时间。如果可能的话,我也在寻找 postgresql 中的解决方案。我更喜欢 postgresql 而不是 dataframe。
Postgres 解决方案可能如下所示:
SELECT
class,
SUM(duration) -- 5
FROM (
SELECT
*,
lead(datetime) OVER (ORDER BY datetime) - datetime as duration -- 4
FROM (
SELECT
*,
COALESCE( -- 2
(class != lag(class) OVER (ORDER BY datetime))::int, -- 1
1
) as state
FROM
t
) s
WHERE state != 0 -- 3
) s
GROUP BY class
lag()
将当前 class
值移动到下一行。可以比较这两个值。如果它们相等,则结果为 0
,否则为 1
COALESCE
只是第一个记录,当然,它不包含以前的值
- 删除所有具有
value = 0
的值(中间步骤)
- 之后,
lead()
值将下一个日期时间值复制到当前行。因此,可以计算下一个和当前 datetime
值之间的差异。现在,我们知道了从一个 class
值更改为另一个值的区别。
- 最终:按
class
分组并对持续时间求和。
您可以只使用 window 函数和聚合:
select class, sum(lead_datetime - datetime) as duration
from (
select t.*, lead(datetime) over(order by datetime) lead_datetime
from mytable t
) t
group by class
对于每一行,这将计算直到下一行的增量持续时间,然后将其关联到当前行的 class
。无需跳过中间步骤,只需将持续时间相加即可。
我有一个由日期时间、class 列组成的数据框。 class 列的值为 'open'、'close'。这是一个物联网数据。我必须计算总开放时间和总关闭时间。数据框是-
index datetime class
------------------------------------------
0 2020-10-05 08:55:00.161326 open
1 2020-10-05 09:00:00.137587 close
2 2020-10-05 09:05:00.089382 close
3 2020-10-05 09:10:00.219278 close
4 2020-10-05 09:15:00.160964 close
5 2020-10-06 09:20:00.315548 close
6 2020-10-06 09:25:00.080932 open
7 2020-10-06 09:30:00.335536 open
8 2020-10-06 09:35:00.202047 close
9 2020-10-06 09:45:00.242022 open
我需要得到的回应是-
index day_count hour_count class
-----------------------------------------------
0 0 0:15:00.097376 open
1 1 23:59:59.918860 close
基本上我正在尝试使用数据捕获传感器的运行时间。如果可能的话,我也在寻找 postgresql 中的解决方案。我更喜欢 postgresql 而不是 dataframe。
Postgres 解决方案可能如下所示:
SELECT
class,
SUM(duration) -- 5
FROM (
SELECT
*,
lead(datetime) OVER (ORDER BY datetime) - datetime as duration -- 4
FROM (
SELECT
*,
COALESCE( -- 2
(class != lag(class) OVER (ORDER BY datetime))::int, -- 1
1
) as state
FROM
t
) s
WHERE state != 0 -- 3
) s
GROUP BY class
lag()
将当前class
值移动到下一行。可以比较这两个值。如果它们相等,则结果为0
,否则为1
COALESCE
只是第一个记录,当然,它不包含以前的值- 删除所有具有
value = 0
的值(中间步骤) - 之后,
lead()
值将下一个日期时间值复制到当前行。因此,可以计算下一个和当前datetime
值之间的差异。现在,我们知道了从一个class
值更改为另一个值的区别。 - 最终:按
class
分组并对持续时间求和。
您可以只使用 window 函数和聚合:
select class, sum(lead_datetime - datetime) as duration
from (
select t.*, lead(datetime) over(order by datetime) lead_datetime
from mytable t
) t
group by class
对于每一行,这将计算直到下一行的增量持续时间,然后将其关联到当前行的 class
。无需跳过中间步骤,只需将持续时间相加即可。