Pandas 如何根据条件将monthy数据转换为nan?

Pandas 如何根据条件将monthy数据转换为nan?,pandas,Pandas,我有这个df: CODE DATE TMAX TMIN PP 0 000130 1991-01-01 32.6 23.4 0.0 1 000130 1991-01-02 31.2 22.4 0.0 2 000130 1991-01-03 32.0 NaN 0.0 3 000130 1991-01-04 32.2 23.0 0.0 4 000130 1991-01-05 30.5

我有这个df:

       CODE      DATE     TMAX  TMIN   PP
0      000130 1991-01-01  32.6  23.4  0.0
1      000130 1991-01-02  31.2  22.4  0.0
2      000130 1991-01-03  32.0   NaN  0.0
3      000130 1991-01-04  32.2  23.0  0.0
4      000130 1991-01-05  30.5  22.0  0.0
      ...        ...   ...   ...  ...
10865  000130 2020-12-31   NaN   NaN  NaN
10866  000132 1991-01-01  35.2   NaN  0.0
10867  000132 1991-01-02  34.6   NaN  0.0
10868  000132 1991-01-03  35.8   NaN  0.0
10869  000132 1991-01-04  34.8   NaN  0.0
仅当一个月内有5个或更多连续的NaN值时,我才希望将月度数据转换为NaN

例如:如果1991年1月TMAX列中有5个或更多连续的NaN值,则TMAX列的所有1991年1月值必须转换为NaN。每年每个月都一样。我需要按代码执行此操作(每个代码值都有1991年1月、1991年2月、2020年12月的TMAX数据)。所以我首先考虑使用
df.groupby['code']
。共有371个代码

对于PP列,仅当一个月内有3个或更多非连续NaN值时,我需要将月度数据转换为NaN。例如:如果1991年1月PP列中有3个非连续的NaN值,则TMAX列的所有1991年1月值必须转换为NaN。每年每个月都一样。我还需要通过代码来实现这一点

我是python的乞丐,所以我会感谢任何帮助

提前感谢。

  • 生成测试数据集的合理代码量
  • 定义要在
    transform()中调用的函数
  • groupby()
  • n是一个参数,因此可用于不同的连续运行
输出 有5个连续的NaN值,因此整个月都被设置为NaN

代码 日期 特敏 TMIN_C 271 00000000 1991-09-29 00:00:00 28.1745 28.1745 272 00000000 1991-09-30 00:00:00 21.1691 21.1691 273 00000000 1991-10-01 00:00:00 28.7848 楠 274 00000000 1991-10-02 00:00:00 22.2346 楠 275 00000000 1991-10-03 00:00:00 22.306 楠 276 00000000 1991-10-04 00:00:00 21.5774 楠 277 00000000 1991-10-05 00:00:00 23.8348 楠 278 00000000 1991-10-06 00:00:00 21.4416 楠 279 00000000 1991-10-07 00:00:00 楠 楠 280 00000000 1991-10-08 00:00:00 楠 楠 281 00000000 1991-10-09 00:00:00 楠 楠 282 00000000 1991-10-10 00:00:00 27.3833 楠 283 00000000 1991-10-11 00:00:00 27.2125 楠 284 00000000 1991-10-12 00:00:00 楠 楠 285 00000000 1991-10-13 00:00:00 楠 楠 286 00000000 1991-10-14 00:00:00 楠 楠 287 00000000 1991-10-15 00:00:00 楠 楠 288 00000000 1991-10-16 00:00:00 楠 楠 289 00000000 1991-10-17 00:00:00 24.8782 楠 290 00000000 1991-10-18 00:00:00 29.7879 楠 291 00000000 1991-10-19 00:00:00 27.0532 楠 292 00000000 1991-10-20 00:00:00 21.3854 楠 293 00000000 1991-10-21 00:00:00 楠 楠 294 00000000 1991-10-22 00:00:00 楠 楠 295 00000000 1991-10-23 00:00:00 23.6399 楠 296 00000000 1991-10-24 00:00:00 楠 楠 297 00000000 1991-10-25 00:00:00 24.7265 楠 298 00000000 1991-10-26 00:00:00 20.2296 楠 299 00000000 1991-10-27 00:00:00 22.0885 楠 300 00000000 1991-10-28 00:00:00 27.3212 楠 301 00000000 1991-10-29 00:00:00 楠 楠
# contruct a CODE / DATE dataframe
df = (pd.DataFrame([f"{i:08d}" for i in range(3)], columns=["CODE"]).assign(foo=1)
 .merge(pd.DataFrame(pd.date_range("01-Jan-1991", "01-Jan-1993"), columns=["DATE"]).assign(foo=1), on="foo")
 .drop(columns="foo")
)


# add a column that has NaNs in it, some will consequetive...
A = np.random.uniform(20,30, len(df))
A.ravel()[np.random.choice(A.size, A.size//3, replace=False)] = np.nan
df["TMIN"] = A

# function that will return NaN if more than n consecutive NaNs
def consecutivenan(d, n=5):
    if d.isnull().astype(int).groupby(d.notnull().astype(int).cumsum()).sum().ge(n).any():
        return np.nan 
    else:
        return d

df["TMIN_C"] = df.groupby(["CODE", df.DATE.dt.year, df.DATE.dt.month], as_index=False)["TMIN"].transform(consecutivenan, n=5)

# demo it's worked
i = df.loc[~df.TMIN.isna() & df.TMIN.ne(df.TMIN_C)].index[0]
df.loc[i-2:i+28]