Path: blob/main/crates/polars-plan/src/dsl/functions/horizontal.rs
8433 views
use super::*;1use crate::prelude::PlanCallback;23/// Accumulate over multiple columns horizontally / row wise.4pub fn fold_exprs<E>(5acc: Expr,6f: PlanCallback<(Series, Series), Series>,7exprs: E,8returns_scalar: bool,9return_dtype: Option<DataTypeExpr>,10) -> Expr11where12E: AsRef<[Expr]>,13{14let mut exprs_v = Vec::with_capacity(exprs.as_ref().len() + 1);15exprs_v.push(acc);16exprs_v.extend(exprs.as_ref().iter().cloned());1718Expr::Function {19input: exprs_v,20function: FunctionExpr::FoldHorizontal {21callback: f,22returns_scalar,23return_dtype,24},25}26}2728/// Analogous to [`Iterator::reduce`](std::iter::Iterator::reduce).29///30/// An accumulator is initialized to the series given by the first expression in `exprs`, and then each subsequent value31/// of the accumulator is computed from `f(acc, next_expr_series)`. If `exprs` is empty, an error is returned when32/// `collect` is called.33pub fn reduce_exprs<E>(34f: PlanCallback<(Series, Series), Series>,35exprs: E,36returns_scalar: bool,37return_dtype: Option<DataTypeExpr>,38) -> Expr39where40E: AsRef<[Expr]>,41{42let exprs = exprs.as_ref().to_vec();4344Expr::Function {45input: exprs,46function: FunctionExpr::ReduceHorizontal {47callback: f,48returns_scalar,49return_dtype,50},51}52}5354/// Accumulate over multiple columns horizontally / row wise.55#[cfg(feature = "dtype-struct")]56pub fn cum_reduce_exprs<E>(57f: PlanCallback<(Series, Series), Series>,58exprs: E,5960returns_scalar: bool,61return_dtype: Option<DataTypeExpr>,62) -> Expr63where64E: AsRef<[Expr]>,65{66let exprs = exprs.as_ref().to_vec();6768Expr::Function {69input: exprs,70function: FunctionExpr::CumReduceHorizontal {71callback: f,72returns_scalar,73return_dtype,74},75}76}7778/// Accumulate over multiple columns horizontally / row wise.79#[cfg(feature = "dtype-struct")]80pub fn cum_fold_exprs<E>(81acc: Expr,82f: PlanCallback<(Series, Series), Series>,83exprs: E,84returns_scalar: bool,85return_dtype: Option<DataTypeExpr>,86include_init: bool,87) -> Expr88where89E: AsRef<[Expr]>,90{91let exprs = exprs.as_ref();92let mut exprs_v = Vec::with_capacity(exprs.len());93exprs_v.push(acc);94exprs_v.extend(exprs.iter().cloned());9596Expr::Function {97input: exprs_v,98function: FunctionExpr::CumFoldHorizontal {99callback: f,100returns_scalar,101return_dtype,102include_init,103},104}105}106107/// Create a new column with the bitwise-and of the elements in each row.108///109/// The name of the resulting column will be "all"; use [`alias`](Expr::alias) to choose a different name.110pub fn all_horizontal<E: AsRef<[Expr]>>(exprs: E) -> PolarsResult<Expr> {111let exprs = exprs.as_ref().to_vec();112polars_ensure!(!exprs.is_empty(), ComputeError: "cannot return empty fold because the number of output rows is unknown");113// This will be reduced to `expr & expr` during conversion to IR.114Ok(Expr::n_ary(115FunctionExpr::Boolean(BooleanFunction::AllHorizontal),116exprs,117))118}119120/// Create a new column with the bitwise-or of the elements in each row.121///122/// The name of the resulting column will be "any"; use [`alias`](Expr::alias) to choose a different name.123pub fn any_horizontal<E: AsRef<[Expr]>>(exprs: E) -> PolarsResult<Expr> {124let exprs = exprs.as_ref().to_vec();125polars_ensure!(!exprs.is_empty(), ComputeError: "cannot return empty fold because the number of output rows is unknown");126// This will be reduced to `expr | expr` during conversion to IR.127Ok(Expr::n_ary(128FunctionExpr::Boolean(BooleanFunction::AnyHorizontal),129exprs,130))131}132133/// Create a new column with the maximum value per row.134///135/// The name of the resulting column will be `"max"`; use [`alias`](Expr::alias) to choose a different name.136pub fn max_horizontal<E: AsRef<[Expr]>>(exprs: E) -> PolarsResult<Expr> {137let exprs = exprs.as_ref().to_vec();138polars_ensure!(!exprs.is_empty(), ComputeError: "cannot return empty fold because the number of output rows is unknown");139Ok(Expr::n_ary(FunctionExpr::MaxHorizontal, exprs))140}141142/// Create a new column with the minimum value per row.143///144/// The name of the resulting column will be `"min"`; use [`alias`](Expr::alias) to choose a different name.145pub fn min_horizontal<E: AsRef<[Expr]>>(exprs: E) -> PolarsResult<Expr> {146let exprs = exprs.as_ref().to_vec();147polars_ensure!(!exprs.is_empty(), ComputeError: "cannot return empty fold because the number of output rows is unknown");148Ok(Expr::n_ary(FunctionExpr::MinHorizontal, exprs))149}150151/// Sum all values horizontally across columns.152pub fn sum_horizontal<E: AsRef<[Expr]>>(exprs: E, ignore_nulls: bool) -> PolarsResult<Expr> {153let exprs = exprs.as_ref().to_vec();154polars_ensure!(!exprs.is_empty(), ComputeError: "cannot return empty fold because the number of output rows is unknown");155Ok(Expr::n_ary(156FunctionExpr::SumHorizontal { ignore_nulls },157exprs,158))159}160161/// Compute the mean of all values horizontally across columns.162pub fn mean_horizontal<E: AsRef<[Expr]>>(exprs: E, ignore_nulls: bool) -> PolarsResult<Expr> {163let exprs = exprs.as_ref().to_vec();164polars_ensure!(!exprs.is_empty(), ComputeError: "cannot return empty fold because the number of output rows is unknown");165Ok(Expr::n_ary(166FunctionExpr::MeanHorizontal { ignore_nulls },167exprs,168))169}170171/// Folds the expressions from left to right keeping the first non-null values.172///173/// It is an error to provide an empty `exprs`.174pub fn coalesce(exprs: &[Expr]) -> Expr {175Expr::n_ary(FunctionExpr::Coalesce, exprs.to_vec())176}177178179