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

如何在Rust中获取Polars DataFrame的差异(通用方法)

获取Polars DataFrame过滤前后的差异行

问题场景

你有如下Polars代码,通过过滤得到新的DataFrame,想要获取被过滤移除的行,且希望用通用方法而非反转原过滤条件:

use polars::prelude::*;

fn main() -> PolarsResult<()> {
    let df = df! (
        "nrs" => &[Some(1), Some(2), Some(3), Some(4), Some(5)],
        "names" => &[Some("foo"), Some("ham"), Some("spam"), Some("eggs"), None],
        "groups" => &["A", "A", "B", "C", "B"],
    )?;

    println!("{:?}", df);

    let df2 = df.lazy().filter(col("nrs").lt(lit(4))).collect()?;

    println!("{:?}", df2);

    Ok(())
}

运行输出:

shape: (5, 3)
┌─────┬───────┬────────┐
│ nrs ┆ names ┆ groups │
│ --- ┆ ---   ┆ ---    │
│ i32 ┆ str   ┆ str    │
╞═════╪═══════╪════════╡
│ 1   ┆ foo   ┆ A      │
│ 2   ┆ ham   ┆ A      │
│ 3   ┆ spam  ┆ B      │
│ 4   ┆ eggs  ┆ C      │
│ 5   ┆ null  ┆ B      │
└─────┴───────┴────────┘
shape: (3, 3)
┌─────┬───────┬────────┐
│ nrs ┆ names ┆ groups │
│ --- ┆ ---   ┆ ---    │
│ i32 ┆ str   ┆ str    │
╞═════╪═══════╪════════╡
│ 1   ┆ foo   ┆ A      │
│ 2   ┆ ham   ┆ A      │
│ 3   ┆ spam  ┆ B      │
└─────┴───────┴────────┘

解决方案:使用anti_join操作

Polars的anti_join方法可以直接返回左表中不存在于右表的行,完美满足需求,且不需要反转原过滤条件。

修改后的代码如下:

use polars::prelude::*;

fn main() -> PolarsResult<()> {
    let df = df! (
        "nrs" => &[Some(1), Some(2), Some(3), Some(4), Some(5)],
        "names" => &[Some("foo"), Some("ham"), Some("spam"), Some("eggs"), None],
        "groups" => &["A", "A", "B", "C", "B"],
    )?;

    println!("原DataFrame:\n{:?}", df);

    let df2 = df.lazy().filter(col("nrs").lt(lit(4))).collect()?;

    println!("过滤后的DataFrame:\n{:?}", df2);

    // 获取被过滤移除的行:原表anti_join过滤后的表
    let removed_rows = df.anti_join(&df2, ["nrs", "names", "groups"])?;
    println!("被移除的行:\n{:?}", removed_rows);

    Ok(())
}

运行输出新增部分:

被移除的行:
shape: (2, 3)
┌─────┬───────┬────────┐
│ nrs ┆ names ┆ groups │
│ --- ┆ ---   ┆ ---    │
│ i32 ┆ str   ┆ str    │
╞═════╪═══════╪════════╡
│ 4   ┆ eggs  ┆ C      │
│ 5   ┆ null  ┆ B      │
└─────┴───────┴────────┘

方法说明

  • anti_join的核心逻辑是:保留左表(原DataFrame)中未在右表(过滤后的DataFrame)找到匹配的所有行,完全对应你要的“被过滤移除的行”。
  • 第二个参数是用于匹配的列列表,这里用全部列确保行的完全匹配;如果你的DataFrame有唯一主键列,仅指定该列会更高效。
  • 这个方法的通用性极强:无论原过滤条件是简单的数值比较还是复杂的多条件组合,都不需要手动反转逻辑,直接通过表之间的关联就能得到差异。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.07.05 18:45:11