11use arrow_buffer:: BooleanBuffer ;
2- use vortex_dtype:: { NativePType , match_each_native_ptype} ;
2+ use vortex_dtype:: { NativePType , Nullability , match_each_native_ptype} ;
33use vortex_error:: VortexResult ;
44
55use crate :: arrays:: { BoolArray , PrimitiveArray , PrimitiveEncoding } ;
@@ -19,8 +19,14 @@ impl BetweenFn<&PrimitiveArray> for PrimitiveEncoding {
1919 return Ok ( None ) ;
2020 } ;
2121
22+ // Note, we know that have checked before that the lower and upper bounds are not constant
23+ // null values
24+
25+ let nullability =
26+ arr. dtype . nullability ( ) | lower. dtype ( ) . nullability ( ) | upper. dtype ( ) . nullability ( ) ;
27+
2228 Ok ( Some ( match_each_native_ptype ! ( arr. ptype( ) , |$P | {
23- between_impl:: <$P >( arr, $P :: try_from( lower) ?, $P :: try_from( upper) ?, options)
29+ between_impl:: <$P >( arr, $P :: try_from( lower) ?, $P :: try_from( upper) ?, nullability , options)
2430 } ) ) )
2531 }
2632}
@@ -29,22 +35,43 @@ fn between_impl<T: NativePType + Copy>(
2935 arr : & PrimitiveArray ,
3036 lower : T ,
3137 upper : T ,
38+ nullability : Nullability ,
3239 options : & BetweenOptions ,
3340) -> ArrayRef {
3441 match ( options. lower_strict , options. upper_strict ) {
3542 // Note: these comparisons are explicitly passed in to allow function impl inlining
36- ( StrictComparison :: Strict , StrictComparison :: Strict ) => {
37- between_impl_ ( arr, lower, NativePType :: is_lt, upper, NativePType :: is_lt)
38- }
39- ( StrictComparison :: Strict , StrictComparison :: NonStrict ) => {
40- between_impl_ ( arr, lower, NativePType :: is_lt, upper, NativePType :: is_le)
41- }
42- ( StrictComparison :: NonStrict , StrictComparison :: Strict ) => {
43- between_impl_ ( arr, lower, NativePType :: is_le, upper, NativePType :: is_lt)
44- }
45- ( StrictComparison :: NonStrict , StrictComparison :: NonStrict ) => {
46- between_impl_ ( arr, lower, NativePType :: is_le, upper, NativePType :: is_le)
47- }
43+ ( StrictComparison :: Strict , StrictComparison :: Strict ) => between_impl_ (
44+ arr,
45+ lower,
46+ NativePType :: is_lt,
47+ upper,
48+ NativePType :: is_lt,
49+ nullability,
50+ ) ,
51+ ( StrictComparison :: Strict , StrictComparison :: NonStrict ) => between_impl_ (
52+ arr,
53+ lower,
54+ NativePType :: is_lt,
55+ upper,
56+ NativePType :: is_le,
57+ nullability,
58+ ) ,
59+ ( StrictComparison :: NonStrict , StrictComparison :: Strict ) => between_impl_ (
60+ arr,
61+ lower,
62+ NativePType :: is_le,
63+ upper,
64+ NativePType :: is_lt,
65+ nullability,
66+ ) ,
67+ ( StrictComparison :: NonStrict , StrictComparison :: NonStrict ) => between_impl_ (
68+ arr,
69+ lower,
70+ NativePType :: is_le,
71+ upper,
72+ NativePType :: is_le,
73+ nullability,
74+ ) ,
4875 }
4976}
5077
@@ -54,6 +81,7 @@ fn between_impl_<T>(
5481 lower_fn : impl Fn ( T , T ) -> bool ,
5582 upper : T ,
5683 upper_fn : impl Fn ( T , T ) -> bool ,
84+ nullability : Nullability ,
5785) -> ArrayRef
5886where
5987 T : NativePType + Copy ,
6593 let i = unsafe { * slice. get_unchecked ( idx) } ;
6694 lower_fn ( lower, i) & upper_fn ( i, upper)
6795 } ) ,
68- arr. validity ( ) . clone ( ) ,
96+ arr. validity ( ) . clone ( ) . union_nullability ( nullability ) ,
6997 )
7098 . into_array ( )
7199}
0 commit comments