You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何在Polars中实现横向向前填充(horizontal forward_fill)

在Polars中实现按列向前填充(等价于pandas的.ffill(axis=1))

需要在Polars中实现行方向的向前填充,效果等价于pandas中的.ffill(axis=1),即对每一行的列从左到右,用左侧最近的非空值填充当前的null值。

示例数据

df = pl.DataFrame(
    {
        "id": ["NY", "TK", "FD"], 
        "eat2000": [1, 6, 3], 
        "eat2001": [-2, None, 4],
        "eat2002": [None, None, None],
        "eat2003": [-9, 3, 8],
        "eat2004": [None, None, 8]
    }
); df

数据输出:

shape: (3, 6)
┌─────┬─────────┬─────────┬─────────┬─────────┬─────────┐
│ id  ┆ eat2000 ┆ eat2001 ┆ eat2002 ┆ eat2003 ┆ eat2004 │
│ --- ┆ ---     ┆ ---     ┆ ---     ┆ ---     ┆ ---     │
│ str ┆ i64     ┆ i64     ┆ f64     ┆ i64     ┆ i64     │
╞═════╪═════════╪═════════╪═════════╪═════════╪═════════╡
│ NY  ┆ 1       ┆ -2      ┆ null    ┆ -9      ┆ null    │
│ TK  ┆ 6       ┆ null    ┆ null    ┆ 3       ┆ null    │
│ FD  ┆ 3       ┆ 4       ┆ null    ┆ 8       ┆ 8       │
└─────┴─────────┴─────────┴─────────┴─────────┴─────────┘

当前实现方式(转Pandas)

pl.from_pandas(df.to_pandas().ffill(axis=1))

效果输出:

shape: (3, 6)
┌─────┬─────────┬─────────┬─────────┬─────────┬─────────┐
│ id  ┆ eat2000 ┆ eat2001 ┆ eat2002 ┆ eat2003 ┆ eat2004 │
│ --- ┆ ---     ┆ ---     ┆ ---     ┆ ---     ┆ ---     │
│ str ┆ i64     ┆ f64     ┆ f64     ┆ i64     ┆ f64     │
╞═════╪═════════╪═════════╪═════════╪═════════╪═════════╡
│ NY  ┆ 1       ┆ -2.0    ┆ -2.0    ┆ -9      ┆ -9.0    │
│ TK  ┆ 6       ┆ 6.0     ┆ 6.0     ┆ 3       ┆ 3.0     │
│ FD  ┆ 3       ┆ 4.0     ┆ 4.0     ┆ 8       ┆ 8.0     │
└─────┴─────────┴─────────┴─────────┴─────────┴─────────┘

Polars原生实现方式

方法一:列表转换+向前填充+结构体展开

通过将行内列转换为列表,执行向前填充后再拆回原列结构:

# 指定需要填充的列(排除id列)
fill_columns = df.columns[1:]

df_ffill = df.with_columns(
    pl.concat_list(fill_columns)
    .list.forward_fill()  # 对列表内元素执行行方向向前填充
    .list.to_struct(fields=fill_columns)  # 将填充后的列表转回结构体
    .alias("filled_cols")
).unnest("filled_cols")  # 展开结构体为原列

print(df_ffill)

方法二:pl.fold逐列累积非空值

使用pl.fold函数逐列累积每一行的最近非空值,实现行方向填充:

fill_columns = df.columns[1:]

df_ffill = df.with_columns(
    pl.fold(
        acc=None,
        func=lambda acc, col: pl.coalesce(col, acc),  # 优先取当前列值,否则用累积的非空值
        exprs=fill_columns
    ).alias(col) for col in fill_columns
)

print(df_ffill)

两种方法均能得到与Pandas.ffill(axis=1)完全一致的结果,且保留Polars的原生性能优势。


内容的提问来源于stack exchange,提问作者codedancer

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.17 22:50:28