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

如何在Polars LazyFrame中按列名模式选择多列并生成计算表达式

如何在Polars LazyFrame中按列名模式选择多列并生成计算表达式

我太懂这种纠结了——想用LazyFrame的延迟计算优势,又要按列名模式批量做运算,还得避开那个烦人的列名解析性能警告。其实Polars的表达式和选择器系统已经给我们准备好了非常灵活的解决方案,完全不用硬啃df.columns。

下面给你两种实用的方法,都能完美解决你的需求:

方法一:用选择器(Selectors)动态生成表达式(推荐)

这种方法完全不需要提前获取列名,直接利用Polars的selectors匹配列模式,然后动态生成运算表达式,从根源上避免性能警告。

针对你的场景(给每个_low列匹配对应的_high列并相加),代码可以这么写:

import polars as pl
from polars import selectors as cs

# 你的原始LazyFrame
df = pl.from_repr("""
shape: (5, 4)
┌─────────┬──────────┬───────────┬────────────┐
│ red_low ┆ red_high ┆ green_low ┆ green_high │
│ ---     ┆ ---      ┆ ---       ┆ ---        │
│ i64     ┆ i64      ┆ i64       ┆ i64        │
╞═════════╪══════════╪═══════════╪════════════╡
│ 1       ┆ 10       ┆ 2         ┆ 20         │
│ 2       ┆ 20       ┆ 3         ┆ 30         │
│ 3       ┆ 30       ┆ 4         ┆ 40         │
│ 4       ┆ 40       ┆ 5         ┆ 50         │
│ 5       ┆ 50       ┆ 6         ┆ 60         │
└─────────┴──────────┴───────────┴────────────┘
""").lazy()

# 1. 用选择器匹配所有以_low结尾的列
low_columns = cs.ends_with("_low")

# 2. 对每个匹配到的列,动态生成"_low + _high"的表达式
sum_expressions = low_columns.map(
    lambda col: (col + pl.col(col.name.replace("_low", "_high"))).alias(col.name.replace("_low", "_sum"))
)

# 3. 将新列添加到原DataFrame并执行计算
result = df.with_columns(sum_expressions).collect()
print(result)

运行后就会得到你想要的结果,而且全程不会触发性能警告——因为我们完全是在表达式层面处理,没有提前解析LazyFrame的列名集合。

方法二:从Schema安全提取列名(适合需要自定义前缀逻辑的场景)

如果你需要更复杂的前缀处理逻辑(比如列名的分隔符不是_,或者有特殊前缀规则),可以从LazyFrame的schema属性提取列名。这里要注意:只要你的LazyFrame有明确的Schema(比如从已知结构的数据源创建,或手动指定了Schema),访问schema不会触发性能警告——只有当Schema需要动态解析时(比如从无Schema的CSV读取)才会有问题。

示例代码:

# 从Schema中提取所有列名(安全操作,无性能警告)
all_column_names = list(df.schema.keys())

# 提取所有唯一的前缀(比如red、green)
prefixes = {name.rsplit("_", 1)[0] for name in all_column_names if "_" in name}

# 为每个前缀生成相加表达式
sum_expressions = []
for prefix in prefixes:
    sum_expressions.append(
        (pl.col(f"{prefix}_low") + pl.col(f"{prefix}_high")).alias(f"{prefix}_sum")
    )

# 执行计算
result = df.with_columns(sum_expressions).collect()
print(result)

这种方法的优势是前缀逻辑可以完全自定义,比如你可以用正则表达式提取前缀,或者过滤特定前缀的列。

为什么这两种方法比直接用df.columns好?

直接调用df.columns会触发Polars的性能警告,因为它需要强制解析LazyFrame的执行计划来确定列名——而上面两种方法要么完全在表达式/选择器层面处理,要么利用了LazyFrame自带的Schema元数据,不会触发不必要的计划解析,完美保留了LazyFrame的延迟计算优势。

备注:内容来源于stack exchange,提问作者Jay Miller

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.04.14 15:20:28