如何计算DataFrame各列中唯一值的累计持续时长?
计算DataFrame每列唯一值的连续存在总时长
你的初始思路方向是对的,但手动存列表的方式不够高效,且难以关联唯一值和对应时长。推荐用pandas的分组+连续段标记的方法来实现,以下是完整解决方案:
步骤说明
核心思路是先给每个连续相同值的片段打唯一标签,再按标签计算单段时长,最后汇总同一值的所有段时长总和。
1. 构造示例数据
import pandas as pd data = { 'Time': [1.1, 2.2, 3.4, 4.5, 5.6, 6.2, 7.4, 8.5, 9.8, 10.1, 11.2], 'colA': [2, 2, 3, 3, 4, 4, 4, 2, 2, 2, 2], 'colB': [2, 2, 5, 5, 5, 6, 6, 6, 5, 5, 5] } df = pd.DataFrame(data)
2. 定义计算单列时长的函数
def calculate_col_duration(col_name, df): # 生成连续段标签:值发生变化时标签+1,同一连续值共享同一标签 df['segment_tag'] = df[col_name].ne(df[col_name].shift()).cumsum() # 按「列值+连续段标签」分组,计算单段时长(段末时间 - 段初时间) segment_durations = df.groupby([col_name, 'segment_tag'])['Time'].agg( lambda x: x.iloc[-1] - x.iloc[0] ) # 按列值汇总所有连续段的时长总和 total_durations = segment_durations.groupby(level=0).sum().reset_index() # 整理列格式,添加列名和单位 total_durations.columns = ['unique_value', 'Duration'] total_durations['Col_name'] = col_name total_durations['Duration'] = total_durations['Duration'].round(1).astype(str) + 's' # 调整列顺序 return total_durations[['Col_name', 'unique_value', 'Duration']]
3. 遍历所有目标列,合并结果并导出CSV
# 初始化结果DataFrame final_result = pd.DataFrame() # 遍历需要计算的列(排除Time列) for col in ['colA', 'colB']: col_result = calculate_col_duration(col, df.copy()) # 用copy避免修改原DataFrame final_result = pd.concat([final_result, col_result], ignore_index=True) # 打印结果 print(final_result) # 导出为CSV final_result.to_csv('duration_report.csv', index=False)
结果验证
运行后得到的结果与你期望的完全一致:
Col_name unique_value Duration 0 colA 2 3.8s 1 colA 3 1.1s 2 colA 4 1.8s 3 colB 2 1.1s 4 colB 5 3.6s 5 colB 6 2.3s
对你现有逻辑的评估
你第一步用df["answer"] = df['colA'].diff().eq(0)识别连续相同值的思路是正确的,但后续手动存列表的方式会增加代码复杂度,且难以批量处理多列。用ne(df[col_name].shift()).cumsum()生成连续段标签的方式,能直接和pandas的groupby功能结合,更简洁地关联唯一值与对应时长,同时支持批量处理所有目标列。
内容的提问来源于stack exchange,提问作者zeke wonder
相关产品推荐
相关产品推荐

