1use num_traits::ToPrimitive;
5use reifydb_core::value::column::{ColumnWithName, buffer::ColumnBuffer, columns::Columns};
6use reifydb_type::{
7 fragment::Fragment,
8 value::{
9 container::number::NumberContainer,
10 decimal::Decimal,
11 int::Int,
12 r#type::{Type, input_types::InputTypes},
13 uint::Uint,
14 },
15};
16
17use crate::routine::{Function, FunctionKind, Routine, RoutineInfo, context::FunctionContext, error::RoutineError};
18
19pub struct Power {
20 info: RoutineInfo,
21}
22
23impl Default for Power {
24 fn default() -> Self {
25 Self::new()
26 }
27}
28
29impl Power {
30 pub fn new() -> Self {
31 Self {
32 info: RoutineInfo::new("math::power"),
33 }
34 }
35}
36
37fn convert_column_to_type(data: &ColumnBuffer, target: Type, row_count: usize) -> ColumnBuffer {
38 match target {
39 Type::Int1 => {
40 let mut result = Vec::with_capacity(row_count);
41 let mut bitvec = Vec::with_capacity(row_count);
42 for i in 0..row_count {
43 if data.is_defined(i) {
44 result.push(get_as_i8(data, i));
45 bitvec.push(true);
46 } else {
47 result.push(0);
48 bitvec.push(false);
49 }
50 }
51 ColumnBuffer::int1_with_bitvec(result, bitvec)
52 }
53 Type::Int2 => {
54 let mut result = Vec::with_capacity(row_count);
55 let mut bitvec = Vec::with_capacity(row_count);
56 for i in 0..row_count {
57 if data.is_defined(i) {
58 result.push(get_as_i16(data, i));
59 bitvec.push(true);
60 } else {
61 result.push(0);
62 bitvec.push(false);
63 }
64 }
65 ColumnBuffer::int2_with_bitvec(result, bitvec)
66 }
67 Type::Int4 => {
68 let mut result = Vec::with_capacity(row_count);
69 let mut bitvec = Vec::with_capacity(row_count);
70 for i in 0..row_count {
71 if data.is_defined(i) {
72 result.push(get_as_i32(data, i));
73 bitvec.push(true);
74 } else {
75 result.push(0);
76 bitvec.push(false);
77 }
78 }
79 ColumnBuffer::int4_with_bitvec(result, bitvec)
80 }
81 Type::Int8 => {
82 let mut result = Vec::with_capacity(row_count);
83 let mut bitvec = Vec::with_capacity(row_count);
84 for i in 0..row_count {
85 if data.is_defined(i) {
86 result.push(get_as_i64(data, i));
87 bitvec.push(true);
88 } else {
89 result.push(0);
90 bitvec.push(false);
91 }
92 }
93 ColumnBuffer::int8_with_bitvec(result, bitvec)
94 }
95 Type::Int16 => {
96 let mut result = Vec::with_capacity(row_count);
97 let mut bitvec = Vec::with_capacity(row_count);
98 for i in 0..row_count {
99 if data.is_defined(i) {
100 result.push(get_as_i128(data, i));
101 bitvec.push(true);
102 } else {
103 result.push(0);
104 bitvec.push(false);
105 }
106 }
107 ColumnBuffer::int16_with_bitvec(result, bitvec)
108 }
109 Type::Uint1 => {
110 let mut result = Vec::with_capacity(row_count);
111 let mut bitvec = Vec::with_capacity(row_count);
112 for i in 0..row_count {
113 if data.is_defined(i) {
114 result.push(get_as_u8(data, i));
115 bitvec.push(true);
116 } else {
117 result.push(0);
118 bitvec.push(false);
119 }
120 }
121 ColumnBuffer::uint1_with_bitvec(result, bitvec)
122 }
123 Type::Uint2 => {
124 let mut result = Vec::with_capacity(row_count);
125 let mut bitvec = Vec::with_capacity(row_count);
126 for i in 0..row_count {
127 if data.is_defined(i) {
128 result.push(get_as_u16(data, i));
129 bitvec.push(true);
130 } else {
131 result.push(0);
132 bitvec.push(false);
133 }
134 }
135 ColumnBuffer::uint2_with_bitvec(result, bitvec)
136 }
137 Type::Uint4 => {
138 let mut result = Vec::with_capacity(row_count);
139 let mut bitvec = Vec::with_capacity(row_count);
140 for i in 0..row_count {
141 if data.is_defined(i) {
142 result.push(get_as_u32(data, i));
143 bitvec.push(true);
144 } else {
145 result.push(0);
146 bitvec.push(false);
147 }
148 }
149 ColumnBuffer::uint4_with_bitvec(result, bitvec)
150 }
151 Type::Uint8 => {
152 let mut result = Vec::with_capacity(row_count);
153 let mut bitvec = Vec::with_capacity(row_count);
154 for i in 0..row_count {
155 if data.is_defined(i) {
156 result.push(get_as_u64(data, i));
157 bitvec.push(true);
158 } else {
159 result.push(0);
160 bitvec.push(false);
161 }
162 }
163 ColumnBuffer::uint8_with_bitvec(result, bitvec)
164 }
165 Type::Uint16 => {
166 let mut result = Vec::with_capacity(row_count);
167 let mut bitvec = Vec::with_capacity(row_count);
168 for i in 0..row_count {
169 if data.is_defined(i) {
170 result.push(get_as_u128(data, i));
171 bitvec.push(true);
172 } else {
173 result.push(0);
174 bitvec.push(false);
175 }
176 }
177 ColumnBuffer::uint16_with_bitvec(result, bitvec)
178 }
179 Type::Float4 => {
180 let mut result = Vec::with_capacity(row_count);
181 let mut bitvec = Vec::with_capacity(row_count);
182 for i in 0..row_count {
183 if data.is_defined(i) {
184 result.push(get_as_f32(data, i));
185 bitvec.push(true);
186 } else {
187 result.push(0.0);
188 bitvec.push(false);
189 }
190 }
191 ColumnBuffer::float4_with_bitvec(result, bitvec)
192 }
193 Type::Float8 => {
194 let mut result = Vec::with_capacity(row_count);
195 let mut bitvec = Vec::with_capacity(row_count);
196 for i in 0..row_count {
197 if data.is_defined(i) {
198 result.push(get_as_f64(data, i));
199 bitvec.push(true);
200 } else {
201 result.push(0.0);
202 bitvec.push(false);
203 }
204 }
205 ColumnBuffer::float8_with_bitvec(result, bitvec)
206 }
207 Type::Int => {
208 let mut result = Vec::with_capacity(row_count);
209 let mut bitvec = Vec::with_capacity(row_count);
210 for i in 0..row_count {
211 if data.is_defined(i) {
212 result.push(Int::from(get_as_i128(data, i)));
213 bitvec.push(true);
214 } else {
215 result.push(Int::default());
216 bitvec.push(false);
217 }
218 }
219 ColumnBuffer::int_with_bitvec(result, bitvec)
220 }
221 Type::Uint => {
222 let mut result = Vec::with_capacity(row_count);
223 let mut bitvec = Vec::with_capacity(row_count);
224 for i in 0..row_count {
225 if data.is_defined(i) {
226 result.push(Uint::from(get_as_u128(data, i)));
227 bitvec.push(true);
228 } else {
229 result.push(Uint::default());
230 bitvec.push(false);
231 }
232 }
233 ColumnBuffer::uint_with_bitvec(result, bitvec)
234 }
235 Type::Decimal => {
236 let mut result = Vec::with_capacity(row_count);
237 let mut bitvec = Vec::with_capacity(row_count);
238 for i in 0..row_count {
239 if data.is_defined(i) {
240 result.push(Decimal::from(get_as_f64(data, i)));
241 bitvec.push(true);
242 } else {
243 result.push(Decimal::default());
244 bitvec.push(false);
245 }
246 }
247 ColumnBuffer::decimal_with_bitvec(result, bitvec)
248 }
249 _ => data.clone(),
250 }
251}
252
253fn get_as_i8(data: &ColumnBuffer, i: usize) -> i8 {
254 match data {
255 ColumnBuffer::Int1(c) => c.get(i).copied().unwrap_or(0),
256 ColumnBuffer::Uint1(c) => c.get(i).map(|&v| v as i8).unwrap_or(0),
257 _ => 0,
258 }
259}
260
261fn get_as_u8(data: &ColumnBuffer, i: usize) -> u8 {
262 match data {
263 ColumnBuffer::Uint1(c) => c.get(i).copied().unwrap_or(0),
264 ColumnBuffer::Int1(c) => c.get(i).map(|&v| v as u8).unwrap_or(0),
265 _ => 0,
266 }
267}
268
269fn get_as_i16(data: &ColumnBuffer, i: usize) -> i16 {
270 match data {
271 ColumnBuffer::Int1(c) => c.get(i).map(|&v| v as i16).unwrap_or(0),
272 ColumnBuffer::Int2(c) => c.get(i).copied().unwrap_or(0),
273 ColumnBuffer::Uint1(c) => c.get(i).map(|&v| v as i16).unwrap_or(0),
274 _ => 0,
275 }
276}
277
278fn get_as_i32(data: &ColumnBuffer, i: usize) -> i32 {
279 match data {
280 ColumnBuffer::Int1(c) => c.get(i).map(|&v| v as i32).unwrap_or(0),
281 ColumnBuffer::Int2(c) => c.get(i).map(|&v| v as i32).unwrap_or(0),
282 ColumnBuffer::Int4(c) => c.get(i).copied().unwrap_or(0),
283 ColumnBuffer::Uint1(c) => c.get(i).map(|&v| v as i32).unwrap_or(0),
284 ColumnBuffer::Uint2(c) => c.get(i).map(|&v| v as i32).unwrap_or(0),
285 _ => 0,
286 }
287}
288
289fn get_as_i64(data: &ColumnBuffer, i: usize) -> i64 {
290 match data {
291 ColumnBuffer::Int1(c) => c.get(i).map(|&v| v as i64).unwrap_or(0),
292 ColumnBuffer::Int2(c) => c.get(i).map(|&v| v as i64).unwrap_or(0),
293 ColumnBuffer::Int4(c) => c.get(i).map(|&v| v as i64).unwrap_or(0),
294 ColumnBuffer::Int8(c) => c.get(i).copied().unwrap_or(0),
295 ColumnBuffer::Uint1(c) => c.get(i).map(|&v| v as i64).unwrap_or(0),
296 ColumnBuffer::Uint2(c) => c.get(i).map(|&v| v as i64).unwrap_or(0),
297 ColumnBuffer::Uint4(c) => c.get(i).map(|&v| v as i64).unwrap_or(0),
298 _ => 0,
299 }
300}
301
302fn get_as_i128(data: &ColumnBuffer, i: usize) -> i128 {
303 match data {
304 ColumnBuffer::Int1(c) => c.get(i).map(|&v| v as i128).unwrap_or(0),
305 ColumnBuffer::Int2(c) => c.get(i).map(|&v| v as i128).unwrap_or(0),
306 ColumnBuffer::Int4(c) => c.get(i).map(|&v| v as i128).unwrap_or(0),
307 ColumnBuffer::Int8(c) => c.get(i).map(|&v| v as i128).unwrap_or(0),
308 ColumnBuffer::Int16(c) => c.get(i).copied().unwrap_or(0),
309 ColumnBuffer::Uint1(c) => c.get(i).map(|&v| v as i128).unwrap_or(0),
310 ColumnBuffer::Uint2(c) => c.get(i).map(|&v| v as i128).unwrap_or(0),
311 ColumnBuffer::Uint4(c) => c.get(i).map(|&v| v as i128).unwrap_or(0),
312 ColumnBuffer::Uint8(c) => c.get(i).map(|&v| v as i128).unwrap_or(0),
313 _ => 0,
314 }
315}
316
317fn get_as_u16(data: &ColumnBuffer, i: usize) -> u16 {
318 match data {
319 ColumnBuffer::Uint1(c) => c.get(i).map(|&v| v as u16).unwrap_or(0),
320 ColumnBuffer::Uint2(c) => c.get(i).copied().unwrap_or(0),
321 _ => 0,
322 }
323}
324
325fn get_as_u32(data: &ColumnBuffer, i: usize) -> u32 {
326 match data {
327 ColumnBuffer::Uint1(c) => c.get(i).map(|&v| v as u32).unwrap_or(0),
328 ColumnBuffer::Uint2(c) => c.get(i).map(|&v| v as u32).unwrap_or(0),
329 ColumnBuffer::Uint4(c) => c.get(i).copied().unwrap_or(0),
330 _ => 0,
331 }
332}
333
334fn get_as_u64(data: &ColumnBuffer, i: usize) -> u64 {
335 match data {
336 ColumnBuffer::Uint1(c) => c.get(i).map(|&v| v as u64).unwrap_or(0),
337 ColumnBuffer::Uint2(c) => c.get(i).map(|&v| v as u64).unwrap_or(0),
338 ColumnBuffer::Uint4(c) => c.get(i).map(|&v| v as u64).unwrap_or(0),
339 ColumnBuffer::Uint8(c) => c.get(i).copied().unwrap_or(0),
340 _ => 0,
341 }
342}
343
344fn get_as_u128(data: &ColumnBuffer, i: usize) -> u128 {
345 match data {
346 ColumnBuffer::Uint1(c) => c.get(i).map(|&v| v as u128).unwrap_or(0),
347 ColumnBuffer::Uint2(c) => c.get(i).map(|&v| v as u128).unwrap_or(0),
348 ColumnBuffer::Uint4(c) => c.get(i).map(|&v| v as u128).unwrap_or(0),
349 ColumnBuffer::Uint8(c) => c.get(i).map(|&v| v as u128).unwrap_or(0),
350 ColumnBuffer::Uint16(c) => c.get(i).copied().unwrap_or(0),
351 _ => 0,
352 }
353}
354
355fn get_as_f32(data: &ColumnBuffer, i: usize) -> f32 {
356 match data {
357 ColumnBuffer::Int1(c) => c.get(i).map(|&v| v as f32).unwrap_or(0.0),
358 ColumnBuffer::Int2(c) => c.get(i).map(|&v| v as f32).unwrap_or(0.0),
359 ColumnBuffer::Int4(c) => c.get(i).map(|&v| v as f32).unwrap_or(0.0),
360 ColumnBuffer::Int8(c) => c.get(i).map(|&v| v as f32).unwrap_or(0.0),
361 ColumnBuffer::Int16(c) => c.get(i).map(|&v| v as f32).unwrap_or(0.0),
362 ColumnBuffer::Uint1(c) => c.get(i).map(|&v| v as f32).unwrap_or(0.0),
363 ColumnBuffer::Uint2(c) => c.get(i).map(|&v| v as f32).unwrap_or(0.0),
364 ColumnBuffer::Uint4(c) => c.get(i).map(|&v| v as f32).unwrap_or(0.0),
365 ColumnBuffer::Uint8(c) => c.get(i).map(|&v| v as f32).unwrap_or(0.0),
366 ColumnBuffer::Uint16(c) => c.get(i).map(|&v| v as f32).unwrap_or(0.0),
367 ColumnBuffer::Float4(c) => c.get(i).copied().unwrap_or(0.0),
368 ColumnBuffer::Float8(c) => c.get(i).map(|&v| v as f32).unwrap_or(0.0),
369 ColumnBuffer::Int {
370 container,
371 ..
372 } => container.get(i).map(|v| v.0.to_f32().unwrap_or(0.0)).unwrap_or(0.0),
373 ColumnBuffer::Uint {
374 container,
375 ..
376 } => container.get(i).map(|v| v.0.to_f32().unwrap_or(0.0)).unwrap_or(0.0),
377 ColumnBuffer::Decimal {
378 container,
379 ..
380 } => container.get(i).map(|v| v.0.to_f32().unwrap_or(0.0)).unwrap_or(0.0),
381 _ => 0.0,
382 }
383}
384
385fn get_as_f64(data: &ColumnBuffer, i: usize) -> f64 {
386 match data {
387 ColumnBuffer::Int1(c) => c.get(i).map(|&v| v as f64).unwrap_or(0.0),
388 ColumnBuffer::Int2(c) => c.get(i).map(|&v| v as f64).unwrap_or(0.0),
389 ColumnBuffer::Int4(c) => c.get(i).map(|&v| v as f64).unwrap_or(0.0),
390 ColumnBuffer::Int8(c) => c.get(i).map(|&v| v as f64).unwrap_or(0.0),
391 ColumnBuffer::Int16(c) => c.get(i).map(|&v| v as f64).unwrap_or(0.0),
392 ColumnBuffer::Uint1(c) => c.get(i).map(|&v| v as f64).unwrap_or(0.0),
393 ColumnBuffer::Uint2(c) => c.get(i).map(|&v| v as f64).unwrap_or(0.0),
394 ColumnBuffer::Uint4(c) => c.get(i).map(|&v| v as f64).unwrap_or(0.0),
395 ColumnBuffer::Uint8(c) => c.get(i).map(|&v| v as f64).unwrap_or(0.0),
396 ColumnBuffer::Uint16(c) => c.get(i).map(|&v| v as f64).unwrap_or(0.0),
397 ColumnBuffer::Float4(c) => c.get(i).map(|&v| v as f64).unwrap_or(0.0),
398 ColumnBuffer::Float8(c) => c.get(i).copied().unwrap_or(0.0),
399 ColumnBuffer::Int {
400 container,
401 ..
402 } => container.get(i).map(|v| v.0.to_f64().unwrap_or(0.0)).unwrap_or(0.0),
403 ColumnBuffer::Uint {
404 container,
405 ..
406 } => container.get(i).map(|v| v.0.to_f64().unwrap_or(0.0)).unwrap_or(0.0),
407 ColumnBuffer::Decimal {
408 container,
409 ..
410 } => container.get(i).map(|v| v.0.to_f64().unwrap_or(0.0)).unwrap_or(0.0),
411 _ => 0.0,
412 }
413}
414
415fn promote_two(left: Type, right: Type) -> Type {
416 if matches!(left, Type::Any) && matches!(right, Type::Any) {
421 return Type::Any;
422 }
423 if matches!(left, Type::Any) && right.is_number() {
424 return right;
425 }
426 if left.is_number() && matches!(right, Type::Any) {
427 return left;
428 }
429 if matches!(left, Type::Float4 | Type::Float8 | Type::Decimal)
430 || matches!(right, Type::Float4 | Type::Float8 | Type::Decimal)
431 {
432 return Type::Decimal;
433 }
434 if left == Type::Int || right == Type::Int {
435 return Type::Int16;
436 }
437 if left == Type::Uint || right == Type::Uint {
438 if matches!(left, Type::Int1 | Type::Int2 | Type::Int4 | Type::Int8 | Type::Int16)
439 || matches!(right, Type::Int1 | Type::Int2 | Type::Int4 | Type::Int8 | Type::Int16)
440 {
441 return Type::Int16;
442 }
443 return Type::Uint16;
444 }
445 Type::promote(left, right)
446}
447
448impl<'a> Routine<FunctionContext<'a>> for Power {
449 fn info(&self) -> &RoutineInfo {
450 &self.info
451 }
452
453 fn return_type(&self, input_types: &[Type]) -> Type {
454 if input_types.len() >= 2 {
455 promote_two(input_types[0].clone(), input_types[1].clone())
456 } else {
457 Type::Float8
458 }
459 }
460
461 fn execute(&self, ctx: &mut FunctionContext<'a>, args: &Columns) -> Result<Columns, RoutineError> {
462 if args.len() != 2 {
463 return Err(RoutineError::FunctionArityMismatch {
464 function: ctx.fragment.clone(),
465 expected: 2,
466 actual: args.len(),
467 });
468 }
469
470 let base_column = &args[0];
471 let exponent_column = &args[1];
472
473 let (base_data, base_bv) = base_column.unwrap_option();
474 let (exp_data, exp_bv) = exponent_column.unwrap_option();
475 let row_count = base_data.len();
476
477 let result_data = match (base_data, exp_data) {
478 (ColumnBuffer::Int1(base), ColumnBuffer::Int1(exp)) => {
479 let mut result = Vec::with_capacity(row_count);
480 let mut res_bitvec = Vec::with_capacity(row_count);
481 for i in 0..row_count {
482 match (base.get(i), exp.get(i)) {
483 (Some(&b), Some(&e)) => {
484 result.push(if e < 0 {
485 0
486 } else {
487 (b as i32).pow(e as u32)
488 });
489 res_bitvec.push(true);
490 }
491 _ => {
492 result.push(0);
493 res_bitvec.push(false);
494 }
495 }
496 }
497 ColumnBuffer::int4_with_bitvec(result, res_bitvec)
498 }
499 (ColumnBuffer::Int2(base), ColumnBuffer::Int2(exp)) => {
500 let mut result = Vec::with_capacity(row_count);
501 let mut res_bitvec = Vec::with_capacity(row_count);
502 for i in 0..row_count {
503 match (base.get(i), exp.get(i)) {
504 (Some(&b), Some(&e)) => {
505 result.push(if e < 0 {
506 0
507 } else {
508 (b as i32).pow(e as u32)
509 });
510 res_bitvec.push(true);
511 }
512 _ => {
513 result.push(0);
514 res_bitvec.push(false);
515 }
516 }
517 }
518 ColumnBuffer::int4_with_bitvec(result, res_bitvec)
519 }
520 (ColumnBuffer::Int4(base), ColumnBuffer::Int4(exp)) => {
521 let mut result = Vec::with_capacity(row_count);
522 let mut res_bitvec = Vec::with_capacity(row_count);
523 for i in 0..row_count {
524 match (base.get(i), exp.get(i)) {
525 (Some(&b), Some(&e)) => {
526 result.push(if e < 0 {
527 0
528 } else {
529 b.saturating_pow(e as u32)
530 });
531 res_bitvec.push(true);
532 }
533 _ => {
534 result.push(0);
535 res_bitvec.push(false);
536 }
537 }
538 }
539 ColumnBuffer::int4_with_bitvec(result, res_bitvec)
540 }
541 (ColumnBuffer::Int8(base), ColumnBuffer::Int8(exp)) => {
542 let mut result = Vec::with_capacity(row_count);
543 let mut res_bitvec = Vec::with_capacity(row_count);
544 for i in 0..row_count {
545 match (base.get(i), exp.get(i)) {
546 (Some(&b), Some(&e)) => {
547 result.push(if e < 0 {
548 0
549 } else {
550 b.saturating_pow(e as u32)
551 });
552 res_bitvec.push(true);
553 }
554 _ => {
555 result.push(0);
556 res_bitvec.push(false);
557 }
558 }
559 }
560 ColumnBuffer::int8_with_bitvec(result, res_bitvec)
561 }
562 (ColumnBuffer::Int16(base), ColumnBuffer::Int16(exp)) => {
563 let mut result = Vec::with_capacity(row_count);
564 let mut res_bitvec = Vec::with_capacity(row_count);
565 for i in 0..row_count {
566 match (base.get(i), exp.get(i)) {
567 (Some(&b), Some(&e)) => {
568 result.push(if e < 0 {
569 0
570 } else {
571 b.saturating_pow(e as u32)
572 });
573 res_bitvec.push(true);
574 }
575 _ => {
576 result.push(0);
577 res_bitvec.push(false);
578 }
579 }
580 }
581 ColumnBuffer::int16_with_bitvec(result, res_bitvec)
582 }
583 (ColumnBuffer::Float4(base), ColumnBuffer::Float4(exp)) => {
584 let mut result = Vec::with_capacity(row_count);
585 let mut res_bitvec = Vec::with_capacity(row_count);
586 for i in 0..row_count {
587 match (base.get(i), exp.get(i)) {
588 (Some(&b), Some(&e)) => {
589 result.push(b.powf(e));
590 res_bitvec.push(true);
591 }
592 _ => {
593 result.push(0.0);
594 res_bitvec.push(false);
595 }
596 }
597 }
598 ColumnBuffer::float4_with_bitvec(result, res_bitvec)
599 }
600 (ColumnBuffer::Float8(base), ColumnBuffer::Float8(exp)) => {
601 let mut result = Vec::with_capacity(row_count);
602 let mut res_bitvec = Vec::with_capacity(row_count);
603 for i in 0..row_count {
604 match (base.get(i), exp.get(i)) {
605 (Some(&b), Some(&e)) => {
606 result.push(b.powf(e));
607 res_bitvec.push(true);
608 }
609 _ => {
610 result.push(0.0);
611 res_bitvec.push(false);
612 }
613 }
614 }
615 ColumnBuffer::float8_with_bitvec(result, res_bitvec)
616 }
617 (ColumnBuffer::Uint1(base), ColumnBuffer::Uint1(exp)) => {
618 let mut result = Vec::with_capacity(row_count);
619 let mut res_bitvec = Vec::with_capacity(row_count);
620 for i in 0..row_count {
621 match (base.get(i), exp.get(i)) {
622 (Some(&b), Some(&e)) => {
623 result.push((b as u32).saturating_pow(e as u32));
624 res_bitvec.push(true);
625 }
626 _ => {
627 result.push(0);
628 res_bitvec.push(false);
629 }
630 }
631 }
632 ColumnBuffer::uint4_with_bitvec(result, res_bitvec)
633 }
634 (ColumnBuffer::Uint2(base), ColumnBuffer::Uint2(exp)) => {
635 let mut result = Vec::with_capacity(row_count);
636 let mut res_bitvec = Vec::with_capacity(row_count);
637 for i in 0..row_count {
638 match (base.get(i), exp.get(i)) {
639 (Some(&b), Some(&e)) => {
640 result.push((b as u32).saturating_pow(e as u32));
641 res_bitvec.push(true);
642 }
643 _ => {
644 result.push(0);
645 res_bitvec.push(false);
646 }
647 }
648 }
649 ColumnBuffer::uint4_with_bitvec(result, res_bitvec)
650 }
651 (ColumnBuffer::Uint4(base), ColumnBuffer::Uint4(exp)) => {
652 let mut result = Vec::with_capacity(row_count);
653 let mut res_bitvec = Vec::with_capacity(row_count);
654 for i in 0..row_count {
655 match (base.get(i), exp.get(i)) {
656 (Some(&b), Some(&e)) => {
657 result.push(b.saturating_pow(e));
658 res_bitvec.push(true);
659 }
660 _ => {
661 result.push(0);
662 res_bitvec.push(false);
663 }
664 }
665 }
666 ColumnBuffer::uint4_with_bitvec(result, res_bitvec)
667 }
668 (ColumnBuffer::Uint8(base), ColumnBuffer::Uint8(exp)) => {
669 let mut result = Vec::with_capacity(row_count);
670 let mut res_bitvec = Vec::with_capacity(row_count);
671 for i in 0..row_count {
672 match (base.get(i), exp.get(i)) {
673 (Some(&b), Some(&e)) => {
674 result.push(b.saturating_pow(e as u32));
675 res_bitvec.push(true);
676 }
677 _ => {
678 result.push(0);
679 res_bitvec.push(false);
680 }
681 }
682 }
683 ColumnBuffer::uint8_with_bitvec(result, res_bitvec)
684 }
685 (ColumnBuffer::Uint16(base), ColumnBuffer::Uint16(exp)) => {
686 let mut result = Vec::with_capacity(row_count);
687 let mut res_bitvec = Vec::with_capacity(row_count);
688 for i in 0..row_count {
689 match (base.get(i), exp.get(i)) {
690 (Some(&b), Some(&e)) => {
691 result.push(b.saturating_pow(e as u32));
692 res_bitvec.push(true);
693 }
694 _ => {
695 result.push(0);
696 res_bitvec.push(false);
697 }
698 }
699 }
700 ColumnBuffer::uint16_with_bitvec(result, res_bitvec)
701 }
702 (
703 ColumnBuffer::Int {
704 container: base,
705 max_bytes,
706 },
707 ColumnBuffer::Int {
708 container: exp,
709 ..
710 },
711 ) => {
712 let mut result = Vec::with_capacity(row_count);
713 let mut res_bitvec = Vec::with_capacity(row_count);
714 for i in 0..row_count {
715 match (base.get(i), exp.get(i)) {
716 (Some(b), Some(e)) => {
717 let b_val = b.0.to_f64().unwrap_or(0.0);
718 let e_val = e.0.to_f64().unwrap_or(0.0);
719 result.push(Int::from(b_val.powf(e_val) as i64));
720 res_bitvec.push(true);
721 }
722 _ => {
723 result.push(Int::default());
724 res_bitvec.push(false);
725 }
726 }
727 }
728 ColumnBuffer::Int {
729 container: NumberContainer::new(result),
730 max_bytes: *max_bytes,
731 }
732 }
733 (
734 ColumnBuffer::Uint {
735 container: base,
736 max_bytes,
737 },
738 ColumnBuffer::Uint {
739 container: exp,
740 ..
741 },
742 ) => {
743 let mut result = Vec::with_capacity(row_count);
744 let mut res_bitvec = Vec::with_capacity(row_count);
745 for i in 0..row_count {
746 match (base.get(i), exp.get(i)) {
747 (Some(b), Some(e)) => {
748 let b_val = b.0.to_f64().unwrap_or(0.0);
749 let e_val = e.0.to_f64().unwrap_or(0.0);
750 result.push(Uint::from(b_val.powf(e_val) as u64));
751 res_bitvec.push(true);
752 }
753 _ => {
754 result.push(Uint::default());
755 res_bitvec.push(false);
756 }
757 }
758 }
759 ColumnBuffer::Uint {
760 container: NumberContainer::new(result),
761 max_bytes: *max_bytes,
762 }
763 }
764 (
765 ColumnBuffer::Decimal {
766 container: base,
767 precision,
768 scale,
769 },
770 ColumnBuffer::Decimal {
771 container: exp,
772 ..
773 },
774 ) => {
775 let mut result = Vec::with_capacity(row_count);
776 let mut res_bitvec = Vec::with_capacity(row_count);
777 for i in 0..row_count {
778 match (base.get(i), exp.get(i)) {
779 (Some(b), Some(e)) => {
780 let b_val = b.0.to_f64().unwrap_or(0.0);
781 let e_val = e.0.to_f64().unwrap_or(0.0);
782 result.push(Decimal::from(b_val.powf(e_val)));
783 res_bitvec.push(true);
784 }
785 _ => {
786 result.push(Decimal::default());
787 res_bitvec.push(false);
788 }
789 }
790 }
791 ColumnBuffer::Decimal {
792 container: NumberContainer::new(result),
793 precision: *precision,
794 scale: *scale,
795 }
796 }
797 _ => {
799 let base_type = base_data.get_type();
800 let exp_type = exp_data.get_type();
801
802 if !base_type.is_number() || !exp_type.is_number() {
803 return Err(RoutineError::FunctionInvalidArgumentType {
804 function: ctx.fragment.clone(),
805 argument_index: 0,
806 expected: InputTypes::numeric().expected_at(0).to_vec(),
807 actual: base_type,
808 });
809 }
810
811 let promoted_type = promote_two(base_type, exp_type);
812 let promoted_base = convert_column_to_type(base_data, promoted_type.clone(), row_count);
813 let promoted_exp = convert_column_to_type(exp_data, promoted_type, row_count);
814
815 let base_col = ColumnWithName::new(Fragment::internal("base"), promoted_base);
816 let exp_col = ColumnWithName::new(Fragment::internal("exp"), promoted_exp);
817 let promoted_columns = Columns::new(vec![base_col, exp_col]);
818
819 return self.call(ctx, &promoted_columns);
820 }
821 };
822
823 let combined_bitvec = match (base_bv, exp_bv) {
824 (Some(b), Some(e)) => Some(b.and(e)),
825 (Some(b), None) => Some(b.clone()),
826 (None, Some(e)) => Some(e.clone()),
827 (None, None) => None,
828 };
829
830 let final_data = if let Some(bv) = combined_bitvec {
831 ColumnBuffer::Option {
832 inner: Box::new(result_data),
833 bitvec: bv,
834 }
835 } else {
836 result_data
837 };
838
839 Ok(Columns::new(vec![ColumnWithName::new(ctx.fragment.clone(), final_data)]))
840 }
841}
842
843impl Function for Power {
844 fn kinds(&self) -> &[FunctionKind] {
845 &[FunctionKind::Scalar]
846 }
847}