Pandas数据帧的多个列是否可以按不同的值进行切片

2024-10-01 19:26:06 发布

您现在位置:Python中文网/ 问答频道 /正文

我有一个日期-时间索引的数据帧(65列(为了清晰起见,只显示了9列)->传感器数量,x行->观察数(对于示例数据,我将其限制为700行,以说明我遇到的问题)。 演示csv: https://pastebin.com/mpSgJF94

    swp_data = pd.read_csv(FILE_NAME, index_col=0, header=0, parse_dates=True, infer_datetime_format=True)
swp_data = swp_data.sort_index()

对于每一列,我需要找到值是列最大值的95%的点,并计算出从数据帧开始到95%的点,其中时间步长之间的差大于给定值(在本例中为0.2)。在

类似于在R中工作的东西(不是实际的代码,而是一个示例)

^{pr2}$

它将95%的点作为循环的结束索引,并查看时间点之间的差异并返回一个索引值,其中差异大于等于0.2

在熊猫中,我计算了以下内容: 95%值

    s95 = (swp_data.max() + (swp_data.max() * .05))

A1-24,-20.6260635, A1-18,-17.863923, A1-12,-11.605629, A2-24,-16.755144, A2-18,-17.6815275, A2-12,-16.369584, A3-24,-15.5030295

95%时间

    s95_time = (swp_data >= (swp_data.max() + (swp_data.max() * .05))).idxmax()

A1-242011年2月10日1:30, A1-18,2011年3月10日6:20, A1-12,2011年2月10日17:20, A2-242011年3月10日6:10, A2-18,2011年3月10日1:30, A2-12,2011年2月10日17:10, A3-242011年2月10日1:30

到目前为止,我已经有了最大值和95%的值,以及一系列的时间戳,其中每个列都达到了它的95%点。 s95值:

我试图通过创建一个值为<;=95%point的布尔数据帧来屏蔽数据帧(试图复制R的which),并尝试了数据框。在哪里使用值>;=95%。mask和where都没有提供我需要的信息,因为当我开始记录时,有些传感器已经超过了max的95%(mask为这些值返回NaN),而where返回这些值,但不返回低于95%阈值的值。在

我要找的输出应该是

      A1-24, A1-18, A1-12, A2-24, A2-18, A2-12, A3-24, A3-18, A3-12
BREAKING  hh:mm, hh:mm, hh:mm, hh:mm, hh:mm, hh:mm, hh:mm, hh:mm, hh:mm

其中hh:mm等于从数据文件开始到断开值的时间。在

到目前为止,我在SE和google上发现的,让我困惑的是,我是否可以将dataframe的列按不同的值进行子集,并且很难弄清楚我要做的是什么叫做。在

编辑:@pratiek评论:

我要做的是找到一种方法,我可以在某种程度上自动化这个过程,这样使用95%的位置,我可以返回断点。我有大约200个csv文件,我正试图处理,并希望尽可能多的过滤使用95%和打破位置。在


Tags: csv数据a2示例dataindexa1hh
1条回答
网友
1楼 · 发布于 2024-10-01 19:26:06

据我所知,这是一个可能的解决办法。 注意,我在示例中将swap_data重命名为df,并在您的问题中提供的csv示例文件上测试解决方案。在

查找从启动到值达到列最大值的95%时的持续时间

如您所述,查找每个列达到最大值95%的第一个时间点:

idx = (df >= df.max(axis=0) * 1.05).idxmax()

>>> idx
Out[]:
A1-24   2011-10-02 01:30:00
A1-18   2011-10-03 06:20:00
A1-12   2011-10-02 17:20:00
A2-24   2011-10-03 06:10:00
A2-18   2011-10-03 01:30:00
A2-12   2011-10-02 17:10:00
A3-24   2011-10-02 01:30:00
dtype: datetime64[ns]

注意使用df.max() * 1.05避免计算max两次,而{}则是相同的。在

然后通过减去第一个时间戳来计算从数据帧开始的持续时间

^{pr2}$

这是从记录开始到s95点的每一列所花费的时间。 如果第一个记录值已经高于此点,则时间为0。在

屏蔽数据帧以覆盖该时段

mask = pd.concat([pd.Series(df.index)] * df.columns.size, axis=1) < idx.values.T
df_masked = df.where(mask.values)

>>> df_masked.dropna(how='all')
Out[]:
                     A1-24     A1-18     A1-12     A2-24     A2-18     A2-12  A3-24
Timestamp
2011-10-02 01:30:00    NaN -18.63589 -16.90389 -17.26780 -19.20653 -19.59666    NaN
2011-10-02 01:40:00    NaN -18.64686 -16.93100 -17.26832 -19.22702 -19.62036    NaN
2011-10-02 01:50:00    NaN -18.65098 -16.92761 -17.26132 -19.22705 -19.61355    NaN
2011-10-02 02:00:00    NaN -18.64307 -16.94764 -17.27702 -19.22746 -19.63462    NaN
2011-10-02 02:10:00    NaN -18.66338 -16.94900 -17.27325 -19.25358 -19.62761    NaN
2011-10-02 02:20:00    NaN -18.66217 -16.95625 -17.27386 -19.25455 -19.64009    NaN
2011-10-02 02:30:00    NaN -18.66015 -16.96130 -17.27040 -19.25898 -19.64241    NaN
2011-10-02 02:40:00    NaN -18.66883 -16.96980 -17.27580 -19.27054 -19.65454    NaN
2011-10-02 02:50:00    NaN -18.68635 -16.97897 -17.27488 -19.28492 -19.65808    NaN
2011-10-02 03:00:00    NaN -18.68009 -16.99057 -17.28346 -19.28928 -19.67182    NaN
2011-10-02 03:10:00    NaN -18.68450 -17.00258 -17.28196 -19.32272 -19.68135    NaN
2011-10-02 03:20:00    NaN -18.68777 -17.01009 -17.29675 -19.30864 -19.68747    NaN
2011-10-02 03:30:00    NaN -18.70067 -17.01706 -17.29178 -19.32034 -19.69742    NaN
2011-10-02 03:40:00    NaN -18.70095 -17.03559 -17.29352 -19.32741 -19.70945    NaN
2011-10-02 03:50:00    NaN -18.70636 -17.03651 -17.28925 -19.33549 -19.71560    NaN
2011-10-02 04:00:00    NaN -18.70937 -17.03548 -17.28996 -19.33433 -19.71211    NaN
2011-10-02 04:10:00    NaN -18.70599 -17.04444 -17.29223 -19.33740 -19.72227    NaN
2011-10-02 04:20:00    NaN -18.71292 -17.05510 -17.29449 -19.35154 -19.72779    NaN
2011-10-02 04:30:00    NaN -18.72158 -17.06376 -17.28770 -19.35647 -19.73064    NaN
2011-10-02 04:40:00    NaN -18.72185 -17.06910 -17.30018 -19.36785 -19.74481    NaN
2011-10-02 04:50:00    NaN -18.72048 -17.06599 -17.29004 -19.37320 -19.73424    NaN
2011-10-02 05:00:00    NaN -18.73083 -17.07618 -17.29528 -19.37319 -19.75045    NaN
2011-10-02 05:10:00    NaN -18.72215 -17.08587 -17.29650 -19.38400 -19.75713    NaN
2011-10-02 05:20:00    NaN -18.73206 -17.10233 -17.29767 -19.39254 -19.76838    NaN
2011-10-02 05:30:00    NaN -18.73719 -17.09621 -17.29842 -19.39363 -19.76258    NaN
2011-10-02 05:40:00    NaN -18.73839 -17.10910 -17.29237 -19.40390 -19.76864    NaN
2011-10-02 05:50:00    NaN -18.74257 -17.12091 -17.29398 -19.40846 -19.78042    NaN
2011-10-02 06:00:00    NaN -18.74327 -17.12995 -17.29097 -19.41153 -19.77897    NaN
2011-10-02 06:10:00    NaN -18.74326 -17.04482 -17.28397 -19.40928 -19.77430    NaN
2011-10-02 06:20:00    NaN -18.73100 -16.86221 -17.28575 -19.40956 -19.78396    NaN
...                    ...       ...       ...       ...       ...       ...    ...
2011-10-03 01:20:00    NaN -18.16448       NaN -16.99797 -17.95030       NaN    NaN
2011-10-03 01:30:00    NaN -18.15606       NaN -16.98879       NaN       NaN    NaN
2011-10-03 01:40:00    NaN -18.12795       NaN -16.97951       NaN       NaN    NaN
2011-10-03 01:50:00    NaN -18.12974       NaN -16.97937       NaN       NaN    NaN
2011-10-03 02:00:00    NaN -18.11848       NaN -16.96770       NaN       NaN    NaN
2011-10-03 02:10:00    NaN -18.11879       NaN -16.95256       NaN       NaN    NaN
2011-10-03 02:20:00    NaN -18.08212       NaN -16.95461       NaN       NaN    NaN
2011-10-03 02:30:00    NaN -18.09060       NaN -16.94141       NaN       NaN    NaN
2011-10-03 02:40:00    NaN -18.07000       NaN -16.93006       NaN       NaN    NaN
2011-10-03 02:50:00    NaN -18.07461       NaN -16.91700       NaN       NaN    NaN
2011-10-03 03:00:00    NaN -18.06039       NaN -16.91466       NaN       NaN    NaN
2011-10-03 03:10:00    NaN -18.04229       NaN -16.89537       NaN       NaN    NaN
2011-10-03 03:20:00    NaN -18.03514       NaN -16.89753       NaN       NaN    NaN
2011-10-03 03:30:00    NaN -18.03014       NaN -16.88813       NaN       NaN    NaN
2011-10-03 03:40:00    NaN -18.00851       NaN -16.88086       NaN       NaN    NaN
2011-10-03 03:50:00    NaN -18.01028       NaN -16.87721       NaN       NaN    NaN
2011-10-03 04:00:00    NaN -18.00227       NaN -16.86687       NaN       NaN    NaN
2011-10-03 04:10:00    NaN -17.98804       NaN -16.85424       NaN       NaN    NaN
2011-10-03 04:20:00    NaN -17.96740       NaN -16.84466       NaN       NaN    NaN
2011-10-03 04:30:00    NaN -17.96451       NaN -16.84205       NaN       NaN    NaN
2011-10-03 04:40:00    NaN -17.95414       NaN -16.82609       NaN       NaN    NaN
2011-10-03 04:50:00    NaN -17.93661       NaN -16.81903       NaN       NaN    NaN
2011-10-03 05:00:00    NaN -17.92905       NaN -16.80737       NaN       NaN    NaN
2011-10-03 05:10:00    NaN -17.92743       NaN -16.80582       NaN       NaN    NaN
2011-10-03 05:20:00    NaN -17.91504       NaN -16.78991       NaN       NaN    NaN
2011-10-03 05:30:00    NaN -17.89965       NaN -16.78469       NaN       NaN    NaN
2011-10-03 05:40:00    NaN -17.89945       NaN -16.77288       NaN       NaN    NaN
2011-10-03 05:50:00    NaN -17.88822       NaN -16.76610       NaN       NaN    NaN
2011-10-03 06:00:00    NaN -17.87259       NaN -16.75742       NaN       NaN    NaN
2011-10-03 06:10:00    NaN -17.87308       NaN       NaN       NaN       NaN    NaN

[173 rows x 7 columns]

为此,您必须为每列计算一个bool掩码:

  1. 创建一个数据帧,其中DateTimeIndex值与df:pd.concat([pd.Series(df.index)] * df.columns.size, axis=1)相同的列数。 这里df.index必须转换为pd.Series,然后重复以匹配列数df.columns.size

  2. < idx.values.T创建掩码本身,其中values得到idx作为numpy.array,并且{}将其转置,以便按列与数据帧进行比较。

  3. df.where(mask.values)屏蔽数据帧,其中使用values得到的掩码为numpy.array。这是必需的,因为掩码与df没有相同的标签。

  4. (可选)使用.dropna(how='all')

    仅保留至少一个值不是NaN的行

过滤每个时间点之间差异的屏蔽数据

如果我理解得很好的话,您需要在每个时间点之间的difference > 0.2上过滤数据,并且只针对选定的时间段。 我仍然有点不清楚,所以如果我误解了,请不要犹豫在评论中讨论。在

这可以通过以下方式实现:

^{4}$

但不幸的是,对于提供的数据集,没有与这些条件匹配的值。在

>>> df[df_masked.diff(1) > 0.2].any()
Out[]:
A1-24    False
A1-18    False
A1-12    False
A2-24    False
A2-18    False
A2-12    False
A3-24    False
dtype: bool

编辑:将结果可视化为bool数据帧(评论跟进)

使用df_masked.diff(1) > 0.2可以非常简单地将结果可视化为带有索引和列的布尔数据框。 但是,可能会有很多不必要的行只包含False,因此可以通过以下方式对其进行筛选:

df_diff = df_masked.diff(1) > 0.1  # Raising the threshold a bit to get some values

>>> df_diff[df_diff.any(axis=1)]
Out[]:
                     A1-24  A1-18  A1-12  A2-24  A2-18  A2-12  A3-24
Timestamp
2011-10-02 06:20:00  False  False   True  False  False  False  False
2011-10-02 06:30:00  False  False   True  False  False  False  False
2011-10-02 06:40:00  False  False   True  False  False  False  False
2011-10-02 06:50:00  False  False   True  False  False  False  False
2011-10-02 07:00:00  False  False   True  False  False  False  False
2011-10-02 07:10:00  False  False   True  False  False  False  False
2011-10-02 07:20:00  False  False   True  False  False  False  False
2011-10-02 07:30:00  False  False   True  False  False  False  False
2011-10-02 07:40:00  False  False   True  False  False  False  False
2011-10-02 07:50:00  False  False   True  False  False  False  False
2011-10-02 08:00:00  False  False   True  False  False  False  False
2011-10-02 08:10:00  False  False   True  False  False  False  False
2011-10-02 08:20:00  False  False   True  False  False  False  False
2011-10-02 08:30:00  False  False   True  False  False  False  False
2011-10-02 08:40:00  False  False   True  False  False  False  False
2011-10-02 08:50:00  False  False   True  False  False  False  False
2011-10-02 09:00:00  False  False   True  False  False  False  False
2011-10-02 09:10:00  False  False   True  False  False  False  False
2011-10-02 09:20:00  False  False   True  False  False  False  False
2011-10-02 09:30:00  False  False   True  False  False  False  False
2011-10-02 12:20:00  False  False  False  False  False   True  False
2011-10-02 12:50:00  False  False  False  False   True   True  False
2011-10-02 13:10:00  False  False  False  False  False   True  False

相关问题 更多 >

    热门问题