
本文详解如何在 polars 中对 dataframe 按指定列分组,并将目标列值聚合为嵌套列表,涵盖核心语法、关键参数说明、代码示例及常见注意事项。
本文详解如何在 polars 中对 dataframe 按指定列分组,并将目标列值聚合为嵌套列表,涵盖核心语法、关键参数说明、代码示例及常见注意事项。
在 Polars 中实现“按列分组 + 列值转列表”这一常见聚合操作,需使用 group_by() 配合 agg() 方法,而非 Pandas 风格的链式索引(如 df.group_by("a")["b"].apply(list)),后者在 Polars 中会直接报错:TypeError: 'GroupBy' object is not subscriptable。正确做法是显式调用聚合函数,明确指定待聚合的列及其聚合逻辑。
✅ 正确实现方式
核心语法为:
df.group_by("分组列", maintain_order=True).agg(pl.col("目标列"))其中:
- pl.col("目标列") 是 Polars 的列选择表达式,当单独传入 agg() 时,默认行为即为 收集所有值构成列表(list aggregation);
- maintain_order=True 是推荐启用的参数——它确保输出中分组的顺序与原始 DataFrame 中首次出现的顺序一致(例如 "A" 先于 "B" 出现,则结果中 "A" 行排第一)。若不指定,Polars 可能按字典序或内部哈希顺序排列分组,导致结果不可预测。
以下为完整可运行示例:
import polars as pl
df = pl.DataFrame({
"Letter": ["A", "A", "B", "B", "B", "C", "C", "D", "D", "E"],
"Value": [1, 2, 3, 4, 5, 6, 7, 8, 9, 10]
})
result = df.group_by("Letter", maintain_order=True).agg(pl.col("Value"))
print(result)输出结果如下(类型注解清晰,Value 列自动推断为 list[i64]):
┌────────┬───────────┐ │ Letter ┆ Value │ │ --- ┆ --- │ │ str ┆ list[i64] │ ╞════════╪═══════════╡ │ A ┆ [1, 2] │ │ B ┆ [3, 4, 5] │ │ C ┆ [6, 7] │ │ D ┆ [8, 9] │ │ E ┆ [10] │ └────────┴───────────┘
⚠️ 注意事项与进阶提示
- 不可省略 agg():group_by() 返回的是惰性 GroupBy 对象,必须调用 agg()(或其他聚合方法如 len(), sum(), mean())才能触发实际计算。
-
多列聚合更灵活:若需同时对多个列做不同聚合(如 Value 转列表、Count 求和),可传入表达式列表:
df.group_by("Letter").agg([ pl.col("Value").list(), # 显式写法,等价于 pl.col("Value") pl.col("Value").sum().alias("Sum") ]) - 空组处理:若某分组无数据(如过滤后),默认不会出现在结果中;如需保留空列表,需结合 left_join 或 upsample 等策略预定义分组键。
- 性能提示:list 聚合在 Polars 中高度优化,适用于百万级行内分组;但若后续需频繁展开列表(如 explode()),建议评估是否应保持长格式以提升整体 pipeline 效率。
掌握这一模式,即可高效完成 Polars 中绝大多数“分组归集”任务,兼具简洁性与高性能。

















