如何检查 Rust-Polars 列中元素的值是否为 0

huangapple go评论61阅读模式
英文:

How to check if element value in Rust-Polars column is 0

问题

I am trying to account for a zero in the denominator when calculating a normalized percentage deviation from the term in the denominator.

Here is the code snippet -

let out: DataFrame = input_df
    .lazy()
    .with_columns(vec![
        when(col("write") == lit(0.0) && result.wr == 0.0)
            .then(lit(0.0))
            .otherwise((lit(result.wr) - col("write")) / col("write") * lit(100))
            .alias("write%"),
    ])
    .collect()
    .unwrap();

The problem is col("write") == lit(0.0) resolves to false even when the respective element in col("write") is 0.0. I'm unclear why or how to solve it.

col("write") is of type f64, so is result.wr.

I tried changing to just lit(0) which yielded the same result. Not using lit() throws an 'Expected Expr' error.

英文:

I am trying to account for a zero in the denominator when calculating a normalized percentage deviation from the term in the denominator.

Here is the code snippet -

let out: DataFrame = input_df
    .lazy()
    .with_columns(vec![
        when(col("write") == lit(0.0) && result.wr == 0.0)
            .then(lit(0.0))
            .otherwise((lit(result.wr) - col("write")) / col("write") * lit(100))
            .alias("write%"),
    ])
    .collect()
    .unwrap();

The problem is col("write") == lit(0.0) resolves to false even when the respective element in col("write") is 0.0. I'm unclear why or how to solve it.

col("write") is of type f64, so is result.wr.

I tried changing to just lit(0) which yielded the same result. Not using lit() throws a 'Expected Expr' error.

答案1

得分: 1

这里有一些问题。首先是逻辑问题。您表示要考虑分母中的零,然而以下一行仅在零在分母中分子为零时才会评估为true:

when(col("write") == lit(0.0) && result.wr == 0.0)

第二个问题涉及到==,在比较列值和文字值时,您应该使用内置的列表达式。在这种情况下,您可以使用col("write").eq(lit(0.0))

以下是一个工作示例,注意我删除了分子检查,因为它不是必要的:

let mut input_df = df!("write" => &[0.0, 3.0, 999.0]).unwrap();
let wr = 66.0;

let out: DataFrame = input_df
	.lazy()
	.with_columns(vec![
		when(col("write").eq(lit(0.0)))
			.then(lit(0.0))
			.otherwise((lit(wr) - col("write")) / col("write") * lit(100))
			.alias("write%"),
	])
	.collect()
	.unwrap();

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

输出如下:

形状:(3, 2)

┌───────┬────────────┐
 write  write%     
 ---    ---        
 f64    f64        
╞═══════╪════════════╡
 0.0    0.0        
 3.0    2100.0     
 999.0  -93.393393 
└───────┴────────────┘
英文:

There are a few issues here. The first being a logical one. You are stating you want to account for a zero in the denominator, however the following line will only ever evaluate to true if zero is in the denominator and the numerator:

when(col("write") == lit(0.0) && result.wr == 0.0)

The second issue is with the ==, when comparing column values to literals, you should be using the built-in expressions for the columns. In this case, you can use col("write").eq(lit(0.0)).

Here's a working example, note that I removed the numerator check as it's not needed:

let mut input_df = df!("write" => &[0.0, 3.0, 999.0]).unwrap();
let wr = 66.0;

let out: DataFrame = input_df
	.lazy()
	.with_columns(vec![
			when(col("write").eq(lit(0.0)))
					.then(lit(0.0))
					.otherwise((lit(wr) - col("write")) / col("write") * lit(100))
					.alias("write%"),
	])
	.collect()
	.unwrap();

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

And the output:

shape: (3, 2)

┌───────┬────────────┐
│ write ┆ write%     │
│ ---   ┆ ---        │
│ f64   ┆ f64        │
╞═══════╪════════════╡
│ 0.0   ┆ 0.0        │
│ 3.0   ┆ 2100.0     │
│ 999.0 ┆ -93.393393 │
└───────┴────────────┘

huangapple
  • 本文由 发表于 2023年4月20日 05:30:00
  • 转载请务必保留本文链接:https://go.coder-hub.com/76058948.html
匿名

发表评论

匿名网友

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen:

确定