Skip to main content

vortex_array/expr/exprs/like/
kernel.rs

1// SPDX-License-Identifier: Apache-2.0
2// SPDX-FileCopyrightText: Copyright the Vortex contributors
3
4use vortex_error::VortexExpect;
5use vortex_error::VortexResult;
6
7use crate::Array;
8use crate::ArrayRef;
9use crate::ExecutionCtx;
10use crate::arrays::ExactScalarFn;
11use crate::arrays::ScalarFnArrayView;
12use crate::arrays::ScalarFnVTable;
13use crate::expr::Like as LikeExpr;
14use crate::expr::exprs::like::LikeOptions;
15use crate::kernel::ExecuteParentKernel;
16use crate::optimizer::rules::ArrayParentReduceRule;
17use crate::vtable::VTable;
18
19/// Like pattern matching on an array without reading buffers.
20///
21/// This trait is for like implementations that can operate purely on array metadata
22/// and structure without needing to read or execute on the underlying buffers.
23/// Implementations should return `None` if the operation requires buffer access.
24///
25/// Dispatch is on child 0 (the input). The `pattern` and `options` are extracted from
26/// the parent `ScalarFnArray`.
27pub trait LikeReduce: VTable {
28    fn like(
29        array: &Self::Array,
30        pattern: &dyn Array,
31        options: LikeOptions,
32    ) -> VortexResult<Option<ArrayRef>>;
33}
34
35/// Like pattern matching on an array, potentially reading buffers.
36///
37/// Unlike [`LikeReduce`], this trait is for like implementations that may need
38/// to read and execute on the underlying buffers to produce the result.
39///
40/// Dispatch is on child 0 (the input). The `pattern` and `options` are extracted from
41/// the parent `ScalarFnArray`.
42pub trait LikeKernel: VTable {
43    fn like(
44        array: &Self::Array,
45        pattern: &dyn Array,
46        options: LikeOptions,
47        ctx: &mut ExecutionCtx,
48    ) -> VortexResult<Option<ArrayRef>>;
49}
50
51/// Adaptor that wraps a [`LikeReduce`] impl as an [`ArrayParentReduceRule`].
52#[derive(Default, Debug)]
53pub struct LikeReduceAdaptor<V>(pub V);
54
55impl<V> ArrayParentReduceRule<V> for LikeReduceAdaptor<V>
56where
57    V: LikeReduce,
58{
59    type Parent = ExactScalarFn<LikeExpr>;
60
61    fn reduce_parent(
62        &self,
63        array: &V::Array,
64        parent: ScalarFnArrayView<'_, LikeExpr>,
65        child_idx: usize,
66    ) -> VortexResult<Option<ArrayRef>> {
67        if child_idx != 0 {
68            return Ok(None);
69        }
70        let scalar_fn_array = parent
71            .as_opt::<ScalarFnVTable>()
72            .vortex_expect("ExactScalarFn matcher confirmed ScalarFnArray");
73        let children = scalar_fn_array.children();
74        let pattern = &*children[1];
75        let options = *parent.options;
76        <V as LikeReduce>::like(array, pattern, options)
77    }
78}
79
80/// Adaptor that wraps a [`LikeKernel`] impl as an [`ExecuteParentKernel`].
81#[derive(Default, Debug)]
82pub struct LikeExecuteAdaptor<V>(pub V);
83
84impl<V> ExecuteParentKernel<V> for LikeExecuteAdaptor<V>
85where
86    V: LikeKernel,
87{
88    type Parent = ExactScalarFn<LikeExpr>;
89
90    fn execute_parent(
91        &self,
92        array: &V::Array,
93        parent: ScalarFnArrayView<'_, LikeExpr>,
94        child_idx: usize,
95        ctx: &mut ExecutionCtx,
96    ) -> VortexResult<Option<ArrayRef>> {
97        if child_idx != 0 {
98            return Ok(None);
99        }
100        let scalar_fn_array = parent
101            .as_opt::<ScalarFnVTable>()
102            .vortex_expect("ExactScalarFn matcher confirmed ScalarFnArray");
103        let children = scalar_fn_array.children();
104        let pattern = &*children[1];
105        let options = *parent.options;
106        <V as LikeKernel>::like(array, pattern, options, ctx)
107    }
108}