1use vortex_array::ArrayRef;
5use vortex_array::ArrayView;
6use vortex_array::ExecutionCtx;
7use vortex_array::scalar::PValue;
8use vortex_array::scalar::Scalar;
9use vortex_array::search_sorted::SearchResult;
10use vortex_array::search_sorted::SearchSorted;
11use vortex_array::search_sorted::SearchSortedSide;
12use vortex_array::vtable::OperationsVTable;
13use vortex_error::VortexResult;
14
15use crate::RunEnd;
16use crate::array::RunEndArrayExt;
17
18impl OperationsVTable<RunEnd> for RunEnd {
19 fn scalar_at(
20 array: ArrayView<'_, RunEnd>,
21 index: usize,
22 ctx: &mut ExecutionCtx,
23 ) -> VortexResult<Scalar> {
24 array
25 .values()
26 .execute_scalar(array.find_physical_index(index)?, ctx)
27 }
28}
29
30pub(crate) fn find_slice_end_index(array: &ArrayRef, index: usize) -> VortexResult<usize> {
35 let result = array
36 .as_primitive_typed()
37 .search_sorted(&PValue::from(index), SearchSortedSide::Right)?;
38 Ok(match result {
39 SearchResult::Found(i) => i,
40 SearchResult::NotFound(i) => {
41 if i == array.len() {
42 i
43 } else {
44 i + 1
45 }
46 }
47 })
48}
49
50#[cfg(test)]
51mod tests {
52
53 use vortex_array::IntoArray;
54 use vortex_array::LEGACY_SESSION;
55 use vortex_array::VortexSessionExecute;
56 use vortex_array::aggregate_fn::fns::is_constant::is_constant;
57 use vortex_array::arrays::PrimitiveArray;
58 use vortex_array::assert_arrays_eq;
59 use vortex_array::dtype::DType;
60 use vortex_array::dtype::Nullability;
61 use vortex_array::dtype::PType;
62 use vortex_buffer::buffer;
63
64 use crate::RunEnd;
65
66 #[test]
67 fn slice_array() {
68 let arr = RunEnd::try_new(
69 buffer![2u32, 5, 10].into_array(),
70 buffer![1i32, 2, 3].into_array(),
71 )
72 .unwrap()
73 .slice(3..8)
74 .unwrap();
75 assert_eq!(
76 arr.dtype(),
77 &DType::Primitive(PType::I32, Nullability::NonNullable)
78 );
79 assert_eq!(arr.len(), 5);
80
81 let expected = PrimitiveArray::from_iter(vec![2i32, 2, 3, 3, 3]).into_array();
82 assert_arrays_eq!(arr, expected);
83 }
84
85 #[test]
86 fn double_slice() {
87 let arr = RunEnd::try_new(
88 buffer![2u32, 5, 10].into_array(),
89 buffer![1i32, 2, 3].into_array(),
90 )
91 .unwrap()
92 .slice(3..8)
93 .unwrap();
94 assert_eq!(arr.len(), 5);
95
96 let doubly_sliced = arr.slice(0..3).unwrap();
97
98 let expected = PrimitiveArray::from_iter(vec![2i32, 2, 3]).into_array();
99 assert_arrays_eq!(doubly_sliced, expected);
100 }
101
102 #[test]
103 fn slice_end_inclusive() {
104 let arr = RunEnd::try_new(
105 buffer![2u32, 5, 10].into_array(),
106 buffer![1i32, 2, 3].into_array(),
107 )
108 .unwrap()
109 .slice(4..10)
110 .unwrap();
111 assert_eq!(
112 arr.dtype(),
113 &DType::Primitive(PType::I32, Nullability::NonNullable)
114 );
115 assert_eq!(arr.len(), 6);
116
117 let expected = PrimitiveArray::from_iter(vec![2i32, 3, 3, 3, 3, 3]).into_array();
118 assert_arrays_eq!(arr, expected);
119 }
120
121 #[test]
122 fn slice_at_end() {
123 let re_array = RunEnd::try_new(
124 buffer![7_u64, 10].into_array(),
125 buffer![2_u64, 3].into_array(),
126 )
127 .unwrap();
128
129 assert_eq!(re_array.len(), 10);
130
131 let sliced_array = re_array.slice(re_array.len()..re_array.len()).unwrap();
132 assert!(sliced_array.is_empty());
133 }
134
135 #[test]
136 fn slice_single_end() {
137 let re_array = RunEnd::try_new(
138 buffer![7_u64, 10].into_array(),
139 buffer![2_u64, 3].into_array(),
140 )
141 .unwrap();
142
143 assert_eq!(re_array.len(), 10);
144
145 let sliced_array = re_array.slice(2..5).unwrap();
146
147 let mut ctx = LEGACY_SESSION.create_execution_ctx();
148 assert!(is_constant(&sliced_array, &mut ctx).unwrap())
149 }
150
151 #[test]
152 fn ree_scalar_at_end() {
153 let scalar = RunEnd::encode(buffer![1, 1, 1, 4, 4, 4, 2, 2, 5, 5, 5, 5].into_array())
154 .unwrap()
155 .execute_scalar(11, &mut LEGACY_SESSION.create_execution_ctx())
156 .unwrap();
157 assert_eq!(scalar, 5.into());
158 }
159
160 #[test]
161 fn slice_along_run_boundaries() {
162 let arr = RunEnd::try_new(
165 buffer![3u32, 6, 8, 12].into_array(),
166 buffer![1i32, 4, 2, 5].into_array(),
167 )
168 .unwrap();
169
170 let slice1 = arr.slice(0..3).unwrap();
172 assert_eq!(slice1.len(), 3);
173 let expected = PrimitiveArray::from_iter(vec![1i32, 1, 1]).into_array();
174 assert_arrays_eq!(slice1, expected);
175
176 let slice2 = arr.slice(3..6).unwrap();
178 assert_eq!(slice2.len(), 3);
179 let expected = PrimitiveArray::from_iter(vec![4i32, 4, 4]).into_array();
180 assert_arrays_eq!(slice2, expected);
181
182 let slice3 = arr.slice(6..8).unwrap();
184 assert_eq!(slice3.len(), 2);
185 let expected = PrimitiveArray::from_iter(vec![2i32, 2]).into_array();
186 assert_arrays_eq!(slice3, expected);
187
188 let slice4 = arr.slice(8..12).unwrap();
190 assert_eq!(slice4.len(), 4);
191 let expected = PrimitiveArray::from_iter(vec![5i32, 5, 5, 5]).into_array();
192 assert_arrays_eq!(slice4, expected);
193
194 let slice5 = arr.slice(3..8).unwrap();
196 assert_eq!(slice5.len(), 5);
197 let expected = PrimitiveArray::from_iter(vec![4i32, 4, 4, 2, 2]).into_array();
198 assert_arrays_eq!(slice5, expected);
199
200 let slice6 = arr.slice(1..6).unwrap();
202 assert_eq!(slice6.len(), 5);
203 let expected = PrimitiveArray::from_iter(vec![1i32, 1, 4, 4, 4]).into_array();
204 assert_arrays_eq!(slice6, expected);
205
206 let slice7 = arr.slice(3..7).unwrap();
208 assert_eq!(slice7.len(), 4);
209 let expected = PrimitiveArray::from_iter(vec![4i32, 4, 4, 2]).into_array();
210 assert_arrays_eq!(slice7, expected);
211 }
212}