Skip to main content

arrow_cast/cast/
mod.rs

1// Licensed to the Apache Software Foundation (ASF) under one
2// or more contributor license agreements.  See the NOTICE file
3// distributed with this work for additional information
4// regarding copyright ownership.  The ASF licenses this file
5// to you under the Apache License, Version 2.0 (the
6// "License"); you may not use this file except in compliance
7// with the License.  You may obtain a copy of the License at
8//
9//   http://www.apache.org/licenses/LICENSE-2.0
10//
11// Unless required by applicable law or agreed to in writing,
12// software distributed under the License is distributed on an
13// "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
14// KIND, either express or implied.  See the License for the
15// specific language governing permissions and limitations
16// under the License.
17
18//! Cast kernels to convert [`ArrayRef`]  between supported datatypes.
19//!
20//! See [`cast_with_options`] for more information on specific conversions.
21//!
22//! Example:
23//!
24//! ```
25//! # use arrow_array::*;
26//! # use arrow_cast::cast;
27//! # use arrow_schema::DataType;
28//! # use std::sync::Arc;
29//! # use arrow_array::types::Float64Type;
30//! # use arrow_array::cast::AsArray;
31//! // int32 to float64
32//! let a = Int32Array::from(vec![5, 6, 7]);
33//! let b = cast(&a, &DataType::Float64).unwrap();
34//! let c = b.as_primitive::<Float64Type>();
35//! assert_eq!(5.0, c.value(0));
36//! assert_eq!(6.0, c.value(1));
37//! assert_eq!(7.0, c.value(2));
38//! ```
39
40mod binary;
41mod decimal;
42mod dictionary;
43mod list;
44mod map;
45mod numeric;
46mod run_array;
47mod string;
48mod structs;
49mod temporal;
50mod union;
51
52use crate::cast::binary::*;
53use crate::cast::decimal::*;
54use crate::cast::dictionary::*;
55use crate::cast::list::*;
56use crate::cast::map::*;
57pub(crate) use crate::cast::numeric::{
58    cast_bool_to_numeric, cast_numeric_arrays, cast_numeric_to_bool,
59};
60pub use crate::cast::numeric::{cast_num_to_bool, num_cast, single_bool_to_numeric};
61use crate::cast::run_array::*;
62use crate::cast::string::*;
63use crate::cast::structs::*;
64use crate::cast::temporal::*;
65pub use crate::cast::union::*;
66
67use chrono::{TimeZone, Utc};
68use std::cmp::Ordering;
69use std::sync::Arc;
70
71use crate::display::{ArrayFormatter, FormatOptions};
72use crate::parse::{
73    Parser, parse_interval_day_time, parse_interval_month_day_nano, parse_interval_year_month,
74    string_to_datetime,
75};
76use arrow_array::{builder::*, cast::*, temporal_conversions::*, timezone::Tz, types::*, *};
77use arrow_buffer::{ArrowNativeType, OffsetBuffer, i256};
78use arrow_data::ArrayData;
79use arrow_data::transform::MutableArrayData;
80use arrow_schema::*;
81use arrow_select::take::take;
82use num_traits::{NumCast, ToPrimitive, cast::AsPrimitive};
83
84pub use decimal::{DecimalCast, float_to_decimal, float_to_decimal_opt, rescale_decimal};
85#[expect(deprecated)]
86pub use decimal::{parse_string_to_decimal_native, single_float_to_decimal};
87pub use string::cast_single_string_to_boolean_default;
88
89/// Integers below 2^53 convert to an `f64` exactly.
90const F64_EXACT_INT_LIMIT: f64 = 9_007_199_254_740_992.0;
91/// Integers below 2^24 convert to an `f32` exactly.
92const F32_EXACT_INT_LIMIT: f64 = 16_777_216.0;
93
94/// Lossy conversion from decimal to float.
95///
96/// Returns the `f64` nearest to the decimal's exact value, rounding once, for any
97/// scale that fits in an `i8` -- as every Arrow decimal's does.
98///
99/// Conversion is lossy and follows standard floating point semantics. Values
100/// that exceed the representable range become `INFINITY` or `-INFINITY` without
101/// returning an error.
102#[inline(always)]
103pub fn single_decimal_to_float_lossy<D, F>(f: &F, x: D::Native, scale: i32) -> f64
104where
105    D: DecimalType,
106    F: Fn(D::Native) -> f64,
107{
108    let unscaled = f(x);
109    // Both operands are exact in this range, so this rounds once. A negative scale
110    // multiplies, since `10^-scale` is the exact power of ten there.
111    if (-22..=22).contains(&scale) && unscaled.abs() < F64_EXACT_INT_LIMIT {
112        return if scale >= 0 {
113            unscaled / 10_f64.powi(scale)
114        } else {
115            unscaled * 10_f64.powi(-scale)
116        };
117    }
118    match i8::try_from(scale) {
119        Ok(scale) => decimal_to_f64_rounded_once::<D>(x, scale, unscaled),
120        Err(_) => unscaled / 10_f64.powi(scale),
121    }
122}
123
124/// Rounds once for the values the arithmetic cannot convert exactly, by parsing
125/// the decimal's own text.
126#[cold]
127#[inline(never)]
128fn decimal_to_f64_rounded_once<D: DecimalType>(x: D::Native, scale: i8, unscaled: f64) -> f64 {
129    // `format_decimal` always writes a decimal literal, so the parse cannot fail.
130    // The fallback is there to keep that from being a panic, not because it runs.
131    D::format_decimal(x, u8::MAX, scale)
132        .parse::<f64>()
133        .unwrap_or_else(|_| unscaled / 10_f64.powi(scale.into()))
134}
135
136/// As [`decimal_to_f64_rounded_once`], but narrowing to `f32` in one step.
137/// Rounding to `f64` first and then to `f32` rounds twice: a decimal just above an
138/// `f32` midpoint can collapse onto that midpoint in `f64`, and round-half-even
139/// then sends it the wrong way.
140#[cold]
141#[inline(never)]
142fn decimal_to_f32_rounded_once<D: DecimalType>(x: D::Native, scale: i8, unscaled: f64) -> f32 {
143    // Unreachable, as in [`decimal_to_f64_rounded_once`].
144    D::format_decimal(x, u8::MAX, scale)
145        .parse::<f32>()
146        .unwrap_or_else(|_| unscaled as f32 / 10_f32.powi(scale.into()))
147}
148
149/// Casts a decimal array to `Float64`, rounding each value once.
150fn cast_decimal_to_f64<D, F>(
151    array: &dyn Array,
152    as_float: &F,
153    scale: i8,
154) -> Result<ArrayRef, ArrowError>
155where
156    D: DecimalType + ArrowPrimitiveType,
157    F: Fn(D::Native) -> f64,
158{
159    let array = array.as_primitive::<D>();
160    // No power of ten outside this range is exactly representable.
161    if !(-22..=22).contains(&scale) {
162        let values = array
163            .unary::<_, Float64Type>(|x| decimal_to_f64_rounded_once::<D>(x, scale, as_float(x)));
164        return Ok(Arc::new(values));
165    }
166    let pow = 10_f64.powi(scale.unsigned_abs().into());
167    let values = if scale >= 0 {
168        array.unary::<_, Float64Type>(|x| {
169            let unscaled = as_float(x);
170            if unscaled.abs() < F64_EXACT_INT_LIMIT {
171                unscaled / pow
172            } else {
173                decimal_to_f64_rounded_once::<D>(x, scale, unscaled)
174            }
175        })
176    } else {
177        array.unary::<_, Float64Type>(|x| {
178            let unscaled = as_float(x);
179            if unscaled.abs() < F64_EXACT_INT_LIMIT {
180                unscaled * pow
181            } else {
182                decimal_to_f64_rounded_once::<D>(x, scale, unscaled)
183            }
184        })
185    };
186    Ok(Arc::new(values))
187}
188
189/// Casts a decimal array to `Float32`, rounding each value once. Same shape as
190/// [`cast_decimal_to_f64`], with the smaller bounds an `f32` allows: integers are
191/// exact below 2^24, and `10^k` only up to `k = 10`.
192fn cast_decimal_to_f32<D, F>(
193    array: &dyn Array,
194    as_float: &F,
195    scale: i8,
196) -> Result<ArrayRef, ArrowError>
197where
198    D: DecimalType + ArrowPrimitiveType,
199    F: Fn(D::Native) -> f64,
200{
201    let array = array.as_primitive::<D>();
202    // No power of ten outside this range is exactly representable.
203    if !(-10..=10).contains(&scale) {
204        let values = array
205            .unary::<_, Float32Type>(|x| decimal_to_f32_rounded_once::<D>(x, scale, as_float(x)));
206        return Ok(Arc::new(values));
207    }
208    let pow = 10_f32.powi(scale.unsigned_abs().into());
209    let values = if scale >= 0 {
210        array.unary::<_, Float32Type>(|x| {
211            let unscaled = as_float(x);
212            if unscaled.abs() < F32_EXACT_INT_LIMIT {
213                unscaled as f32 / pow
214            } else {
215                decimal_to_f32_rounded_once::<D>(x, scale, unscaled)
216            }
217        })
218    } else {
219        array.unary::<_, Float32Type>(|x| {
220            let unscaled = as_float(x);
221            if unscaled.abs() < F32_EXACT_INT_LIMIT {
222                unscaled as f32 * pow
223            } else {
224                decimal_to_f32_rounded_once::<D>(x, scale, unscaled)
225            }
226        })
227    };
228    Ok(Arc::new(values))
229}
230
231/// CastOptions provides a way to override the default cast behaviors
232#[derive(Debug, Clone, PartialEq, Eq, Hash)]
233pub struct CastOptions<'a> {
234    /// how to handle cast failures, either return NULL (safe=true) or return ERR (safe=false)
235    pub safe: bool,
236    /// Formatting options when casting from temporal types to string
237    pub format_options: FormatOptions<'a>,
238}
239
240impl Default for CastOptions<'_> {
241    fn default() -> Self {
242        Self {
243            safe: true,
244            format_options: FormatOptions::default(),
245        }
246    }
247}
248
249/// Return true if a value of type `from_type` can be cast into a value of `to_type`.
250///
251/// See [`cast_with_options`] for more information
252pub fn can_cast_types(from_type: &DataType, to_type: &DataType) -> bool {
253    use self::DataType::*;
254    use self::IntervalUnit::*;
255    use self::TimeUnit::*;
256    if from_type == to_type {
257        return true;
258    }
259
260    match (from_type, to_type) {
261        (Null, _) => true,
262        // Dictionary/List conditions should be put in front of others
263        (Dictionary(_, from_value_type), Dictionary(_, to_value_type)) => {
264            can_cast_types(from_value_type, to_value_type)
265        }
266        (Dictionary(_, value_type), _) => can_cast_types(value_type, to_type),
267        (Union(fields, _), _) => union::resolve_child_array(fields, to_type).is_some(),
268        (_, Union(_, _)) => false,
269        (RunEndEncoded(_, value_type), _) => can_cast_types(value_type.data_type(), to_type),
270        (_, RunEndEncoded(_, value_type)) => can_cast_types(from_type, value_type.data_type()),
271        (_, Dictionary(_, value_type)) => can_cast_types(from_type, value_type),
272        (
273            List(list_from) | LargeList(list_from) | ListView(list_from) | LargeListView(list_from),
274            List(list_to) | LargeList(list_to) | ListView(list_to) | LargeListView(list_to),
275        ) => can_cast_types(list_from.data_type(), list_to.data_type()),
276        (
277            List(list_from) | LargeList(list_from) | ListView(list_from) | LargeListView(list_from),
278            Utf8 | LargeUtf8 | Utf8View,
279        ) => can_cast_types(list_from.data_type(), to_type),
280        (
281            FixedSizeList(list_from, _),
282            List(list_to) | LargeList(list_to) | ListView(list_to) | LargeListView(list_to),
283        ) => can_cast_types(list_from.data_type(), list_to.data_type()),
284        (
285            List(list_from) | LargeList(list_from) | ListView(list_from) | LargeListView(list_from),
286            FixedSizeList(list_to, _),
287        ) => can_cast_types(list_from.data_type(), list_to.data_type()),
288        (FixedSizeList(inner, size), FixedSizeList(inner_to, size_to)) if size == size_to => {
289            can_cast_types(inner.data_type(), inner_to.data_type())
290        }
291        (_, List(list_to) | LargeList(list_to) | ListView(list_to) | LargeListView(list_to)) => {
292            can_cast_types(from_type, list_to.data_type())
293        }
294        (_, FixedSizeList(list_to, size)) if *size == 1 => {
295            can_cast_types(from_type, list_to.data_type())
296        }
297        (FixedSizeList(list_from, size), _) if *size == 1 => {
298            can_cast_types(list_from.data_type(), to_type)
299        }
300        (Map(from_entries, ordered_from), Map(to_entries, ordered_to))
301            if ordered_from == ordered_to =>
302        {
303            match (
304                key_field(from_entries),
305                key_field(to_entries),
306                value_field(from_entries),
307                value_field(to_entries),
308            ) {
309                (Some(from_key), Some(to_key), Some(from_value), Some(to_value)) => {
310                    can_cast_types(from_key.data_type(), to_key.data_type())
311                        && can_cast_types(from_value.data_type(), to_value.data_type())
312                }
313                _ => false,
314            }
315        }
316        // cast one decimal type to another decimal type
317        (
318            Decimal32(_, _) | Decimal64(_, _) | Decimal128(_, _) | Decimal256(_, _),
319            Decimal32(_, _) | Decimal64(_, _) | Decimal128(_, _) | Decimal256(_, _),
320        ) => true,
321        // unsigned integer to decimal
322        (
323            UInt8 | UInt16 | UInt32 | UInt64,
324            Decimal32(_, _) | Decimal64(_, _) | Decimal128(_, _) | Decimal256(_, _),
325        ) => true,
326        // signed numeric to decimal
327        (
328            Int8 | Int16 | Int32 | Int64 | Float16 | Float32 | Float64,
329            Decimal32(_, _) | Decimal64(_, _) | Decimal128(_, _) | Decimal256(_, _),
330        ) => true,
331        // decimal to unsigned numeric
332        (
333            Decimal32(_, _) | Decimal64(_, _) | Decimal128(_, _) | Decimal256(_, _),
334            UInt8 | UInt16 | UInt32 | UInt64,
335        ) => true,
336        // decimal to signed numeric
337        (
338            Decimal32(_, _) | Decimal64(_, _) | Decimal128(_, _) | Decimal256(_, _),
339            Null | Int8 | Int16 | Int32 | Int64 | Float16 | Float32 | Float64,
340        ) => true,
341        // decimal to string
342        (
343            Decimal32(_, _) | Decimal64(_, _) | Decimal128(_, _) | Decimal256(_, _),
344            Utf8View | Utf8 | LargeUtf8,
345        ) => true,
346        // string to decimal
347        (
348            Utf8View | Utf8 | LargeUtf8,
349            Decimal32(_, _) | Decimal64(_, _) | Decimal128(_, _) | Decimal256(_, _),
350        ) => true,
351        (Struct(from_fields), Struct(to_fields)) => {
352            if from_fields.len() != to_fields.len() {
353                return false;
354            }
355
356            // fast path, all field names are in the same order and same number of fields
357            if from_fields
358                .iter()
359                .zip(to_fields.iter())
360                .all(|(f1, f2)| f1.name() == f2.name())
361            {
362                return from_fields.iter().zip(to_fields.iter()).all(|(f1, f2)| {
363                    // Assume that nullability between two structs are compatible, if not,
364                    // cast kernel will return error.
365                    can_cast_types(f1.data_type(), f2.data_type())
366                });
367            }
368
369            // slow path, we match the fields by name
370            if to_fields.iter().all(|to_field| {
371                from_fields
372                    .iter()
373                    .find(|from_field| from_field.name() == to_field.name())
374                    .is_some_and(|from_field| {
375                        // Assume that nullability between two structs are compatible, if not,
376                        // cast kernel will return error.
377                        can_cast_types(from_field.data_type(), to_field.data_type())
378                    })
379            }) {
380                return true;
381            }
382
383            // if we couldn't match by name, we try to see if they can be matched by position
384            from_fields
385                .iter()
386                .zip(to_fields.iter())
387                .all(|(f1, f2)| can_cast_types(f1.data_type(), f2.data_type()))
388        }
389        (Struct(_), _) => false,
390        (_, Struct(_)) => false,
391        (_, Boolean) => from_type.is_integer() || from_type.is_floating() || from_type.is_string(),
392        (Boolean, _) => to_type.is_integer() || to_type.is_floating() || to_type.is_string(),
393
394        (Binary, LargeBinary | Utf8 | LargeUtf8 | FixedSizeBinary(_) | BinaryView | Utf8View) => {
395            true
396        }
397        (LargeBinary, Binary | Utf8 | LargeUtf8 | FixedSizeBinary(_) | BinaryView | Utf8View) => {
398            true
399        }
400        (FixedSizeBinary(_), Binary | LargeBinary | BinaryView) => true,
401        (
402            Utf8 | LargeUtf8 | Utf8View,
403            Binary
404            | LargeBinary
405            | Utf8
406            | LargeUtf8
407            | Date32
408            | Date64
409            | Time32(Second | Millisecond)
410            | Time64(Microsecond | Nanosecond)
411            | Timestamp(Second | Millisecond | Microsecond | Nanosecond, _)
412            | Interval(_)
413            | BinaryView,
414        ) => true,
415        (Utf8 | LargeUtf8, Utf8View) => true,
416        (BinaryView, Binary | LargeBinary | Utf8 | LargeUtf8 | Utf8View) => true,
417        (Utf8View | Utf8 | LargeUtf8, _) => to_type.is_numeric(),
418        (_, Utf8 | Utf8View | LargeUtf8) => from_type.is_primitive(),
419
420        (_, Binary | LargeBinary) => from_type.is_integer(),
421
422        // start numeric casts
423        (
424            UInt8 | UInt16 | UInt32 | UInt64 | Int8 | Int16 | Int32 | Int64 | Float16 | Float32
425            | Float64,
426            UInt8 | UInt16 | UInt32 | UInt64 | Int8 | Int16 | Int32 | Int64 | Float16 | Float32
427            | Float64,
428        ) => true,
429        // end numeric casts
430
431        // temporal casts
432        (Int32, Date32 | Date64 | Time32(_)) => true,
433        (Date32, Int32 | Int64) => true,
434        (Time32(_), Int32 | Int64) => true,
435        (Int64, Date64 | Date32 | Time64(_)) => true,
436        (Date64, Int64 | Int32) => true,
437        (Time64(_), Int64) => true,
438        (Date32 | Date64, Date32 | Date64) => true,
439        // time casts
440        (Time32(_), Time32(_)) => true,
441        (Time32(_), Time64(_)) => true,
442        (Time64(_), Time64(_)) => true,
443        (Time64(_), Time32(to_unit)) => {
444            matches!(to_unit, Second | Millisecond)
445        }
446        (Timestamp(_, _), _) if to_type.is_numeric() => true,
447        (_, Timestamp(_, _)) if from_type.is_numeric() => true,
448        (Date64, Timestamp(_, _)) => true,
449        (Date32, Timestamp(_, _)) => true,
450        (
451            Timestamp(_, _),
452            Timestamp(_, _)
453            | Date32
454            | Date64
455            | Time32(Second | Millisecond)
456            | Time64(Microsecond | Nanosecond),
457        ) => true,
458        (_, Duration(_)) if from_type.is_numeric() => true,
459        (Duration(_), _) if to_type.is_numeric() => true,
460        (Duration(_), Duration(_)) => true,
461        // No `(Interval(_), Int64)` arm: `cast_with_options` implements no such cast.
462        (Int32, Interval(to_type)) => match to_type {
463            YearMonth => true,
464            DayTime => false,
465            MonthDayNano => false,
466        },
467        (Duration(_), Interval(MonthDayNano)) => true,
468        (Interval(MonthDayNano), Duration(_)) => true,
469        (Interval(YearMonth), Interval(MonthDayNano)) => true,
470        (Interval(DayTime), Interval(MonthDayNano)) => true,
471        (_, _) => false,
472    }
473}
474
475/// Cast `array` to the provided data type and return a new Array with type `to_type`, if possible.
476///
477/// See [`cast_with_options`] for more information
478pub fn cast(array: &dyn Array, to_type: &DataType) -> Result<ArrayRef, ArrowError> {
479    cast_with_options(array, to_type, &CastOptions::default())
480}
481
482/// Convert an integer to a decimal native value without wrapping.
483///
484/// `AsPrimitive` / `as` silently truncates when the source is wider than `M`
485/// (for example `5_000_000_000i64 as i32`). All integer sources fit in `i128`
486/// losslessly, which [`DecimalCast`] then converts to the decimal native type
487/// with a range check. For types that always fit (e.g. `i64` to `Decimal128`) this
488/// should get optimized to being equivalent to `i64 as i128`.
489fn integer_to_decimal_native<I, M>(value: I) -> Option<M>
490where
491    I: Into<i128>,
492    M: DecimalCast,
493{
494    M::from_decimal(value.into())
495}
496
497/// Returns true if every value of `array` has at most `digits` decimal digits.
498///
499/// If the source type cannot hold that many digits, every value fits;
500/// otherwise the data is scanned, including null slots, since `unary`
501/// converts those as well.
502fn integers_fit_digits<T>(array: &PrimitiveArray<T>, digits: u32) -> bool
503where
504    T: ArrowPrimitiveType,
505    T::Native: ArrowNativeTypeOp,
506{
507    let Ok(bound) = T::Native::usize_as(10).pow_checked(digits) else {
508        // The type's maximum is below the bound, and its minimum, one larger
509        // in magnitude, is a power of two that no power of ten can equal.
510        return true;
511    };
512    let hi = bound.sub_wrapping(T::Native::ONE);
513    // Unsigned types have no negative values to bound.
514    let lo = T::Native::ZERO.sub_checked(hi).unwrap_or(T::Native::ZERO);
515
516    // The scan works in chunks, so an array that does not fit is rejected after
517    // its first failing chunk. Each chunk is checked without branching, so it
518    // vectorizes.
519    array
520        .values()
521        .chunks(64)
522        .all(|chunk| chunk.iter().fold(true, |ok, &v| ok & (v >= lo) & (v <= hi)))
523}
524
525fn cast_integer_to_decimal<
526    T: ArrowPrimitiveType,
527    D: DecimalType + ArrowPrimitiveType<Native = M>,
528    M,
529>(
530    array: &PrimitiveArray<T>,
531    precision: u8,
532    scale: i8,
533    cast_options: &CastOptions,
534) -> Result<ArrayRef, ArrowError>
535where
536    <T as ArrowPrimitiveType>::Native: ArrowNativeTypeOp + Into<i128>,
537    M: ArrowNativeTypeOp + DecimalCast,
538{
539    let overflow = |v: T::Native| {
540        ArrowError::CastError(format!(
541            "Cannot cast to {}({precision}, {scale}). Overflowing on {v:?}",
542            D::PREFIX,
543        ))
544    };
545
546    // An invalid precision or scale would let the bound below admit values the
547    // decimal native type cannot hold, so reject it before choosing a kernel.
548    validate_decimal_precision_and_scale::<D>(precision, scale)?;
549
550    // Scan for values that don't fit in the target type before choosing a
551    // kernel: in the common case that all values fit, the cast is infallible
552    // and we can use the `unary` kernel, which is very fast. Empirically, the
553    // cost of doing the out-of-range scan is small relative to the win from
554    // using a faster kernel.
555    //
556    // A value fits when it has at most `precision - scale` decimal digits: a
557    // nonnegative scale appends that many trailing zeros, and a negative scale
558    // removes digits first. Validation guarantees the difference is not
559    // negative.
560    let digits = (precision as i32 - scale as i32) as u32;
561    let all_fit = integers_fit_digits(array, digits);
562
563    let array = if scale < 0 {
564        // Compute the scale factor once in the source type. Scaling before the
565        // checked conversion permits values that only fit the decimal native
566        // type after scaling.
567        //
568        // scale_factor is always > 0, so div_wrapping(scale_factor) can never
569        // overflow/panic
570        let scale_factor = T::Native::usize_as(10)
571            .pow_checked(scale.unsigned_abs() as u32)
572            .ok();
573
574        match (scale_factor, cast_options.safe) {
575            (Some(scale_factor), _) if all_fit => array.unary::<_, D>(|v| {
576                integer_to_decimal_native::<_, M>(v.div_wrapping(scale_factor))
577                    .expect("value fits the decimal")
578            }),
579            (Some(scale_factor), true) => array.unary_opt::<_, D>(|v| {
580                let v = integer_to_decimal_native::<_, M>(v.div_wrapping(scale_factor))?;
581                (D::is_valid_decimal_precision(v, precision)).then_some(v)
582            }),
583            (Some(scale_factor), false) => array.try_unary::<_, D, _>(|v| {
584                let v = integer_to_decimal_native::<_, M>(v.div_wrapping(scale_factor))
585                    .ok_or_else(|| overflow(v))?;
586                D::validate_decimal_precision(v, precision, scale).map(|()| v)
587            })?,
588            // A scale factor that overflows the source type is larger than all
589            // source values, so integer division produces zero.
590            //
591            // For a well formed decimal scale, this path should never be reachable.
592            (None, _) => array.unary::<_, D>(|_| M::ZERO),
593        }
594    } else {
595        let scale_factor = M::usize_as(10)
596            .pow_checked(scale.unsigned_abs() as u32)
597            .map_err(|_| {
598                ArrowError::CastError(format!(
599                    "Cannot cast to {:?}({}, {}). The scale causes overflow.",
600                    D::PREFIX,
601                    precision,
602                    scale,
603                ))
604            })?;
605
606        if all_fit {
607            array.unary::<_, D>(|v| {
608                integer_to_decimal_native::<_, M>(v)
609                    .expect("value fits the decimal")
610                    .mul_wrapping(scale_factor)
611            })
612        } else if cast_options.safe {
613            array.unary_opt::<_, D>(|v| {
614                let v = integer_to_decimal_native::<_, M>(v)
615                    .and_then(|v| v.mul_checked(scale_factor).ok())?;
616                (D::is_valid_decimal_precision(v, precision)).then_some(v)
617            })
618        } else {
619            array.try_unary::<_, D, _>(|v| {
620                let v = integer_to_decimal_native::<_, M>(v)
621                    .ok_or_else(|| overflow(v))
622                    .and_then(|v| v.mul_checked(scale_factor))?;
623                D::validate_decimal_precision(v, precision, scale).map(|()| v)
624            })?
625        }
626    };
627
628    Ok(Arc::new(array.with_precision_and_scale(precision, scale)?))
629}
630
631/// Cast the primitive array using [`PrimitiveArray::reinterpret_cast`]
632fn cast_reinterpret_arrays<I: ArrowPrimitiveType, O: ArrowPrimitiveType<Native = I::Native>>(
633    array: &dyn Array,
634) -> Result<ArrayRef, ArrowError> {
635    Ok(Arc::new(array.as_primitive::<I>().reinterpret_cast::<O>()))
636}
637
638/// Try to cast `array` to `to_type` if possible.
639///
640/// Returns a new Array with type `to_type` if possible.
641///
642/// Accepts [`CastOptions`] to specify cast behavior. See also [`cast()`].
643///
644/// # Behavior
645/// * `Boolean` to `Utf8`, `LargeUtf8`, or `Utf8View`: `true` => `"true"`, `false` => `"false"`
646/// * `Utf8` to `Boolean`: `true`, `yes`, `on`, `1` => `true`, `false`, `no`, `off`, `0` => `false`,
647///   short variants are accepted, other strings return null or error
648/// * `Utf8` to Numeric: strings that can't be parsed to numbers return null, float strings
649///   in integer casts return null
650/// * Numeric to `Boolean`: 0 returns `false`, any other value returns `true`
651/// * `List` to `List`: the underlying data type is cast
652/// * `List` to `FixedSizeList`: the underlying data type is cast. If safe is true and a list element
653///   has the wrong length it will be replaced with NULL, otherwise an error will be returned
654/// * Primitive to `List`: a list array with 1 value per slot is created
655/// * `Date32` and `Date64`: precision lost when going to higher interval
656/// * `Time32` and `Time64`: precision lost when going to higher interval
657/// * `Timestamp` and `Date{32|64}`: precision lost when going to higher interval
658/// * `Timestamp` to `Date32`, `Time32`, or `Time64`: timestamps without a timezone
659///   support the full `i64` range; timestamps with a timezone must lie within Chrono's
660///   date range. If safe is true, a timestamp outside that range or a `Date32` day
661///   count that does not fit in `i32` becomes NULL, otherwise an error is returned
662/// * Temporal to/from backing Primitive: zero-copy with data type change
663/// * `Float16/Float32/Float64` to `Decimal(precision, scale)` rounds to the `scale` decimals
664///   (i.e. casting `6.4999` to `Decimal(10, 1)` becomes `6.5`).
665/// * `Decimal` to `Float16/Float32/Float64` is lossy and values outside the representable
666///   range become `INFINITY` or `-INFINITY` without error.
667///
668/// Unsupported Casts (check with `can_cast_types` before calling):
669/// * To or from `StructArray`
670/// * `List` to `Primitive`
671/// * `Interval` and `Duration`
672///
673/// # Durations and Intervals
674///
675/// Casting integer types directly to interval types such as
676/// [`IntervalMonthDayNano`] is not supported because the meaning of the integer
677/// is ambiguous. For example, the integer  could represent either nanoseconds
678/// or months.
679///
680/// To cast an integer type to an interval type, first convert to a Duration
681/// type, and then cast that to the desired interval type.
682///
683/// For example, to convert an `Int64` representing nanoseconds to an
684/// `IntervalMonthDayNano` you would first convert the `Int64` to a
685/// `DurationNanoseconds`, and then cast that to `IntervalMonthDayNano`.
686///
687/// # Timestamps and Timezones
688///
689/// Timestamps are stored with an optional timezone in Arrow.
690///
691/// ## Casting timestamps to a timestamp without timezone / UTC
692/// ```
693/// # use arrow_array::Int64Array;
694/// # use arrow_array::types::TimestampSecondType;
695/// # use arrow_cast::{cast, display};
696/// # use arrow_array::cast::AsArray;
697/// # use arrow_schema::{DataType, TimeUnit};
698/// // can use "UTC" if chrono-tz feature is enabled, here use offset based timezone
699/// let data_type = DataType::Timestamp(TimeUnit::Second, None);
700/// let a = Int64Array::from(vec![1_000_000_000, 2_000_000_000, 3_000_000_000]);
701/// let b = cast(&a, &data_type).unwrap();
702/// let b = b.as_primitive::<TimestampSecondType>(); // downcast to result type
703/// assert_eq!(2_000_000_000, b.value(1)); // values are the same as the type has no timezone
704/// // use display to show them (note has no trailing Z)
705/// assert_eq!("2033-05-18T03:33:20", display::array_value_to_string(&b, 1).unwrap());
706/// ```
707///
708/// ## Casting timestamps to a timestamp with timezone
709///
710/// Similarly to the previous example, if you cast numeric values to a timestamp
711/// with timezone, the cast kernel will not change the underlying values
712/// but display and other functions will interpret them as being in the provided timezone.
713///
714/// ```
715/// # use arrow_array::Int64Array;
716/// # use arrow_array::types::TimestampSecondType;
717/// # use arrow_cast::{cast, display};
718/// # use arrow_array::cast::AsArray;
719/// # use arrow_schema::{DataType, TimeUnit};
720/// // can use "Americas/New_York" if chrono-tz feature is enabled, here use offset based timezone
721/// let data_type = DataType::Timestamp(TimeUnit::Second, Some("-05:00".into()));
722/// let a = Int64Array::from(vec![1_000_000_000, 2_000_000_000, 3_000_000_000]);
723/// let b = cast(&a, &data_type).unwrap();
724/// let b = b.as_primitive::<TimestampSecondType>(); // downcast to result type
725/// assert_eq!(2_000_000_000, b.value(1)); // values are still the same
726/// // displayed in the target timezone (note the offset -05:00)
727/// assert_eq!("2033-05-17T22:33:20-05:00", display::array_value_to_string(&b, 1).unwrap());
728/// ```
729/// # Casting timestamps without timezone to timestamps with timezone
730///
731/// When casting from a timestamp without timezone to a timestamp with
732/// timezone, the cast kernel interprets the timestamp values as being in
733/// the destination timezone and then adjusts the underlying value to UTC as required
734///
735/// However, note that when casting from a timestamp with timezone BACK to a
736/// timestamp without timezone the cast kernel does not adjust the values.
737///
738/// Thus round trip casting a timestamp without timezone to a timestamp with
739/// timezone and back to a timestamp without timezone results in different
740/// values than the starting values.
741///
742/// ```
743/// # use arrow_array::Int64Array;
744/// # use arrow_array::types::{TimestampSecondType};
745/// # use arrow_cast::{cast, display};
746/// # use arrow_array::cast::AsArray;
747/// # use arrow_schema::{DataType, TimeUnit};
748/// let data_type  = DataType::Timestamp(TimeUnit::Second, None);
749/// let data_type_tz = DataType::Timestamp(TimeUnit::Second, Some("-05:00".into()));
750/// let a = Int64Array::from(vec![1_000_000_000, 2_000_000_000, 3_000_000_000]);
751/// let b = cast(&a, &data_type).unwrap(); // cast to timestamp without timezone
752/// let b = b.as_primitive::<TimestampSecondType>(); // downcast to result type
753/// assert_eq!(2_000_000_000, b.value(1)); // values are still the same
754/// // displayed without a timezone (note lack of offset or Z)
755/// assert_eq!("2033-05-18T03:33:20", display::array_value_to_string(&b, 1).unwrap());
756///
757/// // Convert timestamps without a timezone to timestamps with a timezone
758/// let c = cast(&b, &data_type_tz).unwrap();
759/// let c = c.as_primitive::<TimestampSecondType>(); // downcast to result type
760/// assert_eq!(2_000_018_000, c.value(1)); // value has been adjusted by offset
761/// // displayed with the target timezone offset (-05:00)
762/// assert_eq!("2033-05-18T03:33:20-05:00", display::array_value_to_string(&c, 1).unwrap());
763///
764/// // Convert from timestamp with timezone back to timestamp without timezone
765/// let d = cast(&c, &data_type).unwrap();
766/// let d = d.as_primitive::<TimestampSecondType>(); // downcast to result type
767/// assert_eq!(2_000_018_000, d.value(1)); // value has not been adjusted
768/// // NOTE: the timestamp is adjusted (08:33:20 instead of 03:33:20 as in previous example)
769/// assert_eq!("2033-05-18T08:33:20", display::array_value_to_string(&d, 1).unwrap());
770/// ```
771pub fn cast_with_options(
772    array: &dyn Array,
773    to_type: &DataType,
774    cast_options: &CastOptions,
775) -> Result<ArrayRef, ArrowError> {
776    use DataType::*;
777    let from_type = array.data_type();
778    // clone array if types are the same
779    if from_type == to_type {
780        return Ok(make_array(array.to_data()));
781    }
782    match (from_type, to_type) {
783        (Null, _) => Ok(new_null_array(to_type, array.len())),
784        (RunEndEncoded(index_type, _), _) => match index_type.data_type() {
785            Int16 => run_end_encoded_cast::<Int16Type>(array, to_type, cast_options),
786            Int32 => run_end_encoded_cast::<Int32Type>(array, to_type, cast_options),
787            Int64 => run_end_encoded_cast::<Int64Type>(array, to_type, cast_options),
788            _ => Err(ArrowError::CastError(format!(
789                "Casting from run end encoded type {from_type:?} to {to_type:?} not supported",
790            ))),
791        },
792        (_, RunEndEncoded(index_type, value_type)) => {
793            let array_ref = make_array(array.to_data());
794            match index_type.data_type() {
795                Int16 => cast_to_run_end_encoded::<Int16Type>(
796                    &array_ref,
797                    value_type.data_type(),
798                    cast_options,
799                ),
800                Int32 => cast_to_run_end_encoded::<Int32Type>(
801                    &array_ref,
802                    value_type.data_type(),
803                    cast_options,
804                ),
805                Int64 => cast_to_run_end_encoded::<Int64Type>(
806                    &array_ref,
807                    value_type.data_type(),
808                    cast_options,
809                ),
810                _ => Err(ArrowError::CastError(format!(
811                    "Casting from type {from_type:?} to run end encoded type {to_type:?} not supported",
812                ))),
813            }
814        }
815        (Union(_, _), _) => union_extract_by_type(
816            array.as_any().downcast_ref::<UnionArray>().unwrap(),
817            to_type,
818            cast_options,
819        ),
820        (_, Union(_, _)) => Err(ArrowError::CastError(format!(
821            "Casting from {from_type} to {to_type} not supported"
822        ))),
823        (Dictionary(index_type, _), _) => match **index_type {
824            Int8 => dictionary_cast::<Int8Type>(array, to_type, cast_options),
825            Int16 => dictionary_cast::<Int16Type>(array, to_type, cast_options),
826            Int32 => dictionary_cast::<Int32Type>(array, to_type, cast_options),
827            Int64 => dictionary_cast::<Int64Type>(array, to_type, cast_options),
828            UInt8 => dictionary_cast::<UInt8Type>(array, to_type, cast_options),
829            UInt16 => dictionary_cast::<UInt16Type>(array, to_type, cast_options),
830            UInt32 => dictionary_cast::<UInt32Type>(array, to_type, cast_options),
831            UInt64 => dictionary_cast::<UInt64Type>(array, to_type, cast_options),
832            _ => Err(ArrowError::CastError(format!(
833                "Casting from dictionary type {from_type} to {to_type} not supported",
834            ))),
835        },
836        (_, Dictionary(index_type, value_type)) => match **index_type {
837            Int8 => cast_to_dictionary::<Int8Type>(array, value_type, cast_options),
838            Int16 => cast_to_dictionary::<Int16Type>(array, value_type, cast_options),
839            Int32 => cast_to_dictionary::<Int32Type>(array, value_type, cast_options),
840            Int64 => cast_to_dictionary::<Int64Type>(array, value_type, cast_options),
841            UInt8 => cast_to_dictionary::<UInt8Type>(array, value_type, cast_options),
842            UInt16 => cast_to_dictionary::<UInt16Type>(array, value_type, cast_options),
843            UInt32 => cast_to_dictionary::<UInt32Type>(array, value_type, cast_options),
844            UInt64 => cast_to_dictionary::<UInt64Type>(array, value_type, cast_options),
845            _ => Err(ArrowError::CastError(format!(
846                "Casting from type {from_type} to dictionary type {to_type} not supported",
847            ))),
848        },
849        // Casting between lists of same types (cast inner values)
850        (List(_), List(to)) => cast_list_values::<i32>(array, to, cast_options),
851        (LargeList(_), LargeList(to)) => cast_list_values::<i64>(array, to, cast_options),
852        (FixedSizeList(_, size_from), FixedSizeList(list_to, size_to)) => {
853            if size_from != size_to {
854                return Err(ArrowError::CastError(
855                    "cannot cast fixed-size-list to fixed-size-list with different size".into(),
856                ));
857            }
858            let array = array.as_fixed_size_list();
859            let values = cast_with_options(array.values(), list_to.data_type(), cast_options)?;
860            let nulls = array.nulls().cloned();
861            let len = array.len();
862            Ok(Arc::new(FixedSizeListArray::try_new_with_length(
863                list_to.clone(),
864                *size_from,
865                values,
866                nulls,
867                len,
868            )?))
869        }
870        (ListView(_), ListView(to)) => cast_list_view_values::<i32>(array, to, cast_options),
871        (LargeListView(_), LargeListView(to)) => {
872            cast_list_view_values::<i64>(array, to, cast_options)
873        }
874        // Casting between different types of lists
875        // List
876        (List(_), LargeList(list_to)) => cast_list::<i32, i64>(array, list_to, cast_options),
877        (List(_), FixedSizeList(field, size)) => {
878            cast_list_to_fixed_size_list::<i32>(array, field, *size, cast_options)
879        }
880        (List(_), ListView(list_to)) => {
881            cast_list_to_list_view::<i32, i32>(array, list_to, cast_options)
882        }
883        (List(_), LargeListView(list_to)) => {
884            cast_list_to_list_view::<i32, i64>(array, list_to, cast_options)
885        }
886        // LargeList
887        (LargeList(_), List(list_to)) => cast_list::<i64, i32>(array, list_to, cast_options),
888        (LargeList(_), FixedSizeList(field, size)) => {
889            cast_list_to_fixed_size_list::<i64>(array, field, *size, cast_options)
890        }
891        (LargeList(_), ListView(list_to)) => {
892            cast_list_to_list_view::<i64, i32>(array, list_to, cast_options)
893        }
894        (LargeList(_), LargeListView(list_to)) => {
895            cast_list_to_list_view::<i64, i64>(array, list_to, cast_options)
896        }
897        // ListView
898        (ListView(_), List(list_to)) => {
899            cast_list_view_to_list::<i32, Int32Type>(array, list_to, cast_options)
900        }
901        (ListView(_), LargeList(list_to)) => {
902            cast_list_view_to_list::<i32, Int64Type>(array, list_to, cast_options)
903        }
904        (ListView(_), LargeListView(list_to)) => {
905            cast_list_view::<i32, i64>(array, list_to, cast_options)
906        }
907        (ListView(_), FixedSizeList(field, size)) => {
908            cast_list_view_to_fixed_size_list::<i32>(array, field, *size, cast_options)
909        }
910        // LargeListView
911        (LargeListView(_), LargeList(list_to)) => {
912            cast_list_view_to_list::<i64, Int64Type>(array, list_to, cast_options)
913        }
914        (LargeListView(_), List(list_to)) => {
915            cast_list_view_to_list::<i64, Int32Type>(array, list_to, cast_options)
916        }
917        (LargeListView(_), ListView(list_to)) => {
918            cast_list_view::<i64, i32>(array, list_to, cast_options)
919        }
920        (LargeListView(_), FixedSizeList(field, size)) => {
921            cast_list_view_to_fixed_size_list::<i64>(array, field, *size, cast_options)
922        }
923        // FixedSizeList
924        (FixedSizeList(_, _), List(list_to)) => {
925            cast_fixed_size_list_to_list::<i32>(array, list_to, cast_options)
926        }
927        (FixedSizeList(_, _), LargeList(list_to)) => {
928            cast_fixed_size_list_to_list::<i64>(array, list_to, cast_options)
929        }
930        (FixedSizeList(_, _), ListView(list_to)) => {
931            cast_fixed_size_list_to_list_view::<i32>(array, list_to, cast_options)
932        }
933        (FixedSizeList(_, _), LargeListView(list_to)) => {
934            cast_fixed_size_list_to_list_view::<i64>(array, list_to, cast_options)
935        }
936        // List to/from other types
937        (FixedSizeList(_, size), _) if *size == 1 => {
938            cast_single_element_fixed_size_list_to_values(array, to_type, cast_options)
939        }
940        // NOTE: we could support FSL to string here too but might be confusing
941        //       since behaviour for size 1 would be different (see arm above)
942        (List(_) | LargeList(_) | ListView(_) | LargeListView(_), _) => match to_type {
943            Utf8 => value_to_string::<i32>(array, cast_options),
944            LargeUtf8 => value_to_string::<i64>(array, cast_options),
945            Utf8View => value_to_string_view(array, cast_options),
946            dt => Err(ArrowError::CastError(format!(
947                "Cannot cast LIST to non-list data type {dt}"
948            ))),
949        },
950        (_, List(to)) => cast_values_to_list::<i32>(array, to, cast_options),
951        (_, LargeList(to)) => cast_values_to_list::<i64>(array, to, cast_options),
952        (_, ListView(to)) => cast_values_to_list_view::<i32>(array, to, cast_options),
953        (_, LargeListView(to)) => cast_values_to_list_view::<i64>(array, to, cast_options),
954        (_, FixedSizeList(to, size)) if *size == 1 => {
955            let values = cast_with_options(array, to.data_type(), cast_options)?;
956            let list = FixedSizeListArray::try_new(to.clone(), 1, values, None)?;
957            Ok(Arc::new(list))
958        }
959        // Map
960        (Map(_, ordered1), Map(_, ordered2)) if ordered1 == ordered2 => {
961            cast_map_values(array.as_map(), to_type, cast_options, ordered1.to_owned())
962        }
963        // Decimal to decimal, same width
964        (Decimal32(p1, s1), Decimal32(p2, s2)) => {
965            cast_decimal_to_decimal_same_type::<Decimal32Type>(
966                array.as_primitive(),
967                *p1,
968                *s1,
969                *p2,
970                *s2,
971                cast_options,
972            )
973        }
974        (Decimal64(p1, s1), Decimal64(p2, s2)) => {
975            cast_decimal_to_decimal_same_type::<Decimal64Type>(
976                array.as_primitive(),
977                *p1,
978                *s1,
979                *p2,
980                *s2,
981                cast_options,
982            )
983        }
984        (Decimal128(p1, s1), Decimal128(p2, s2)) => {
985            cast_decimal_to_decimal_same_type::<Decimal128Type>(
986                array.as_primitive(),
987                *p1,
988                *s1,
989                *p2,
990                *s2,
991                cast_options,
992            )
993        }
994        (Decimal256(p1, s1), Decimal256(p2, s2)) => {
995            cast_decimal_to_decimal_same_type::<Decimal256Type>(
996                array.as_primitive(),
997                *p1,
998                *s1,
999                *p2,
1000                *s2,
1001                cast_options,
1002            )
1003        }
1004        // Decimal to decimal, different width
1005        (Decimal32(p1, s1), Decimal64(p2, s2)) => {
1006            cast_decimal_to_decimal::<Decimal32Type, Decimal64Type>(
1007                array.as_primitive(),
1008                *p1,
1009                *s1,
1010                *p2,
1011                *s2,
1012                cast_options,
1013            )
1014        }
1015        (Decimal32(p1, s1), Decimal128(p2, s2)) => {
1016            cast_decimal_to_decimal::<Decimal32Type, Decimal128Type>(
1017                array.as_primitive(),
1018                *p1,
1019                *s1,
1020                *p2,
1021                *s2,
1022                cast_options,
1023            )
1024        }
1025        (Decimal32(p1, s1), Decimal256(p2, s2)) => {
1026            cast_decimal_to_decimal::<Decimal32Type, Decimal256Type>(
1027                array.as_primitive(),
1028                *p1,
1029                *s1,
1030                *p2,
1031                *s2,
1032                cast_options,
1033            )
1034        }
1035        (Decimal64(p1, s1), Decimal32(p2, s2)) => {
1036            cast_decimal_to_decimal::<Decimal64Type, Decimal32Type>(
1037                array.as_primitive(),
1038                *p1,
1039                *s1,
1040                *p2,
1041                *s2,
1042                cast_options,
1043            )
1044        }
1045        (Decimal64(p1, s1), Decimal128(p2, s2)) => {
1046            cast_decimal_to_decimal::<Decimal64Type, Decimal128Type>(
1047                array.as_primitive(),
1048                *p1,
1049                *s1,
1050                *p2,
1051                *s2,
1052                cast_options,
1053            )
1054        }
1055        (Decimal64(p1, s1), Decimal256(p2, s2)) => {
1056            cast_decimal_to_decimal::<Decimal64Type, Decimal256Type>(
1057                array.as_primitive(),
1058                *p1,
1059                *s1,
1060                *p2,
1061                *s2,
1062                cast_options,
1063            )
1064        }
1065        (Decimal128(p1, s1), Decimal32(p2, s2)) => {
1066            cast_decimal_to_decimal::<Decimal128Type, Decimal32Type>(
1067                array.as_primitive(),
1068                *p1,
1069                *s1,
1070                *p2,
1071                *s2,
1072                cast_options,
1073            )
1074        }
1075        (Decimal128(p1, s1), Decimal64(p2, s2)) => {
1076            cast_decimal_to_decimal::<Decimal128Type, Decimal64Type>(
1077                array.as_primitive(),
1078                *p1,
1079                *s1,
1080                *p2,
1081                *s2,
1082                cast_options,
1083            )
1084        }
1085        (Decimal128(p1, s1), Decimal256(p2, s2)) => {
1086            cast_decimal_to_decimal::<Decimal128Type, Decimal256Type>(
1087                array.as_primitive(),
1088                *p1,
1089                *s1,
1090                *p2,
1091                *s2,
1092                cast_options,
1093            )
1094        }
1095        (Decimal256(p1, s1), Decimal32(p2, s2)) => {
1096            cast_decimal_to_decimal::<Decimal256Type, Decimal32Type>(
1097                array.as_primitive(),
1098                *p1,
1099                *s1,
1100                *p2,
1101                *s2,
1102                cast_options,
1103            )
1104        }
1105        (Decimal256(p1, s1), Decimal64(p2, s2)) => {
1106            cast_decimal_to_decimal::<Decimal256Type, Decimal64Type>(
1107                array.as_primitive(),
1108                *p1,
1109                *s1,
1110                *p2,
1111                *s2,
1112                cast_options,
1113            )
1114        }
1115        (Decimal256(p1, s1), Decimal128(p2, s2)) => {
1116            cast_decimal_to_decimal::<Decimal256Type, Decimal128Type>(
1117                array.as_primitive(),
1118                *p1,
1119                *s1,
1120                *p2,
1121                *s2,
1122                cast_options,
1123            )
1124        }
1125        // Decimal to non-decimal
1126        (Decimal32(_, scale), _) if !to_type.is_temporal() => {
1127            cast_from_decimal::<Decimal32Type, _>(
1128                array,
1129                scale,
1130                from_type,
1131                to_type,
1132                |x: i32| x as f64,
1133                cast_options,
1134            )
1135        }
1136        (Decimal64(_, scale), _) if !to_type.is_temporal() => {
1137            cast_from_decimal::<Decimal64Type, _>(
1138                array,
1139                scale,
1140                from_type,
1141                to_type,
1142                |x: i64| x as f64,
1143                cast_options,
1144            )
1145        }
1146        (Decimal128(_, scale), _) if !to_type.is_temporal() => {
1147            cast_from_decimal::<Decimal128Type, _>(
1148                array,
1149                scale,
1150                from_type,
1151                to_type,
1152                |x: i128| x as f64,
1153                cast_options,
1154            )
1155        }
1156        (Decimal256(_, scale), _) if !to_type.is_temporal() => {
1157            cast_from_decimal::<Decimal256Type, _>(
1158                array,
1159                scale,
1160                from_type,
1161                to_type,
1162                |x: i256| x.to_f64().expect("All i256 values fit in f64"),
1163                cast_options,
1164            )
1165        }
1166        // Non-decimal to decimal
1167        (_, Decimal32(precision, scale)) if !from_type.is_temporal() => {
1168            cast_to_decimal::<Decimal32Type, _>(
1169                array,
1170                precision,
1171                scale,
1172                from_type,
1173                to_type,
1174                cast_options,
1175            )
1176        }
1177        (_, Decimal64(precision, scale)) if !from_type.is_temporal() => {
1178            cast_to_decimal::<Decimal64Type, _>(
1179                array,
1180                precision,
1181                scale,
1182                from_type,
1183                to_type,
1184                cast_options,
1185            )
1186        }
1187        (_, Decimal128(precision, scale)) if !from_type.is_temporal() => {
1188            cast_to_decimal::<Decimal128Type, _>(
1189                array,
1190                precision,
1191                scale,
1192                from_type,
1193                to_type,
1194                cast_options,
1195            )
1196        }
1197        (_, Decimal256(precision, scale)) if !from_type.is_temporal() => {
1198            cast_to_decimal::<Decimal256Type, _>(
1199                array,
1200                precision,
1201                scale,
1202                from_type,
1203                to_type,
1204                cast_options,
1205            )
1206        }
1207        (Struct(from_fields), Struct(to_fields)) => cast_struct_to_struct(
1208            array.as_struct(),
1209            from_fields.clone(),
1210            to_fields.clone(),
1211            cast_options,
1212        ),
1213        (Struct(_), _) => Err(ArrowError::CastError(format!(
1214            "Casting from {from_type} to {to_type} not supported"
1215        ))),
1216        (_, Struct(_)) => Err(ArrowError::CastError(format!(
1217            "Casting from {from_type} to {to_type} not supported"
1218        ))),
1219        (_, Boolean) => match from_type {
1220            UInt8 => cast_numeric_to_bool::<UInt8Type>(array),
1221            UInt16 => cast_numeric_to_bool::<UInt16Type>(array),
1222            UInt32 => cast_numeric_to_bool::<UInt32Type>(array),
1223            UInt64 => cast_numeric_to_bool::<UInt64Type>(array),
1224            Int8 => cast_numeric_to_bool::<Int8Type>(array),
1225            Int16 => cast_numeric_to_bool::<Int16Type>(array),
1226            Int32 => cast_numeric_to_bool::<Int32Type>(array),
1227            Int64 => cast_numeric_to_bool::<Int64Type>(array),
1228            Float16 => cast_numeric_to_bool::<Float16Type>(array),
1229            Float32 => cast_numeric_to_bool::<Float32Type>(array),
1230            Float64 => cast_numeric_to_bool::<Float64Type>(array),
1231            Utf8View => cast_utf8view_to_boolean(array, cast_options),
1232            Utf8 => cast_utf8_to_boolean::<i32>(array, cast_options),
1233            LargeUtf8 => cast_utf8_to_boolean::<i64>(array, cast_options),
1234            _ => Err(ArrowError::CastError(format!(
1235                "Casting from {from_type} to {to_type} not supported",
1236            ))),
1237        },
1238        (Boolean, _) => match to_type {
1239            UInt8 => cast_bool_to_numeric::<UInt8Type>(array, cast_options),
1240            UInt16 => cast_bool_to_numeric::<UInt16Type>(array, cast_options),
1241            UInt32 => cast_bool_to_numeric::<UInt32Type>(array, cast_options),
1242            UInt64 => cast_bool_to_numeric::<UInt64Type>(array, cast_options),
1243            Int8 => cast_bool_to_numeric::<Int8Type>(array, cast_options),
1244            Int16 => cast_bool_to_numeric::<Int16Type>(array, cast_options),
1245            Int32 => cast_bool_to_numeric::<Int32Type>(array, cast_options),
1246            Int64 => cast_bool_to_numeric::<Int64Type>(array, cast_options),
1247            Float16 => cast_bool_to_numeric::<Float16Type>(array, cast_options),
1248            Float32 => cast_bool_to_numeric::<Float32Type>(array, cast_options),
1249            Float64 => cast_bool_to_numeric::<Float64Type>(array, cast_options),
1250            Utf8View => cast_bool_to_string::<StringViewArray>(array),
1251            Utf8 => cast_bool_to_string::<StringArray>(array),
1252            LargeUtf8 => cast_bool_to_string::<LargeStringArray>(array),
1253            _ => Err(ArrowError::CastError(format!(
1254                "Casting from {from_type} to {to_type} not supported",
1255            ))),
1256        },
1257        (Utf8, _) => match to_type {
1258            UInt8 => parse_string::<UInt8Type, i32>(array, cast_options),
1259            UInt16 => parse_string::<UInt16Type, i32>(array, cast_options),
1260            UInt32 => parse_string::<UInt32Type, i32>(array, cast_options),
1261            UInt64 => parse_string::<UInt64Type, i32>(array, cast_options),
1262            Int8 => parse_string::<Int8Type, i32>(array, cast_options),
1263            Int16 => parse_string::<Int16Type, i32>(array, cast_options),
1264            Int32 => parse_string::<Int32Type, i32>(array, cast_options),
1265            Int64 => parse_string::<Int64Type, i32>(array, cast_options),
1266            Float16 => parse_string::<Float16Type, i32>(array, cast_options),
1267            Float32 => parse_string::<Float32Type, i32>(array, cast_options),
1268            Float64 => parse_string::<Float64Type, i32>(array, cast_options),
1269            Date32 => parse_string::<Date32Type, i32>(array, cast_options),
1270            Date64 => parse_string::<Date64Type, i32>(array, cast_options),
1271            Binary => Ok(Arc::new(BinaryArray::from(
1272                array.as_string::<i32>().clone(),
1273            ))),
1274            LargeBinary => {
1275                let binary = BinaryArray::from(array.as_string::<i32>().clone());
1276                cast_byte_container::<BinaryType, LargeBinaryType>(&binary)
1277            }
1278            Utf8View => Ok(Arc::new(StringViewArray::from(array.as_string::<i32>()))),
1279            BinaryView => Ok(Arc::new(
1280                StringViewArray::from(array.as_string::<i32>()).to_binary_view(),
1281            )),
1282            LargeUtf8 => cast_byte_container::<Utf8Type, LargeUtf8Type>(array),
1283            Time32(TimeUnit::Second) => parse_string::<Time32SecondType, i32>(array, cast_options),
1284            Time32(TimeUnit::Millisecond) => {
1285                parse_string::<Time32MillisecondType, i32>(array, cast_options)
1286            }
1287            Time64(TimeUnit::Microsecond) => {
1288                parse_string::<Time64MicrosecondType, i32>(array, cast_options)
1289            }
1290            Time64(TimeUnit::Nanosecond) => {
1291                parse_string::<Time64NanosecondType, i32>(array, cast_options)
1292            }
1293            Timestamp(TimeUnit::Second, to_tz) => cast_string_to_timestamp::<
1294                i32,
1295                TimestampSecondType,
1296            >(array, to_tz.as_ref(), cast_options),
1297            Timestamp(TimeUnit::Millisecond, to_tz) => cast_string_to_timestamp::<
1298                i32,
1299                TimestampMillisecondType,
1300            >(
1301                array, to_tz.as_ref(), cast_options
1302            ),
1303            Timestamp(TimeUnit::Microsecond, to_tz) => cast_string_to_timestamp::<
1304                i32,
1305                TimestampMicrosecondType,
1306            >(
1307                array, to_tz.as_ref(), cast_options
1308            ),
1309            Timestamp(TimeUnit::Nanosecond, to_tz) => cast_string_to_timestamp::<
1310                i32,
1311                TimestampNanosecondType,
1312            >(
1313                array, to_tz.as_ref(), cast_options
1314            ),
1315            Interval(IntervalUnit::YearMonth) => {
1316                cast_string_to_year_month_interval::<i32>(array, cast_options)
1317            }
1318            Interval(IntervalUnit::DayTime) => {
1319                cast_string_to_day_time_interval::<i32>(array, cast_options)
1320            }
1321            Interval(IntervalUnit::MonthDayNano) => {
1322                cast_string_to_month_day_nano_interval::<i32>(array, cast_options)
1323            }
1324            _ => Err(ArrowError::CastError(format!(
1325                "Casting from {from_type} to {to_type} not supported",
1326            ))),
1327        },
1328        (Utf8View, _) => match to_type {
1329            UInt8 => parse_string_view::<UInt8Type>(array, cast_options),
1330            UInt16 => parse_string_view::<UInt16Type>(array, cast_options),
1331            UInt32 => parse_string_view::<UInt32Type>(array, cast_options),
1332            UInt64 => parse_string_view::<UInt64Type>(array, cast_options),
1333            Int8 => parse_string_view::<Int8Type>(array, cast_options),
1334            Int16 => parse_string_view::<Int16Type>(array, cast_options),
1335            Int32 => parse_string_view::<Int32Type>(array, cast_options),
1336            Int64 => parse_string_view::<Int64Type>(array, cast_options),
1337            Float16 => parse_string_view::<Float16Type>(array, cast_options),
1338            Float32 => parse_string_view::<Float32Type>(array, cast_options),
1339            Float64 => parse_string_view::<Float64Type>(array, cast_options),
1340            Date32 => parse_string_view::<Date32Type>(array, cast_options),
1341            Date64 => parse_string_view::<Date64Type>(array, cast_options),
1342            Binary => cast_view_to_byte::<StringViewType, GenericBinaryType<i32>>(array),
1343            LargeBinary => cast_view_to_byte::<StringViewType, GenericBinaryType<i64>>(array),
1344            BinaryView => Ok(Arc::new(array.as_string_view().clone().to_binary_view())),
1345            Utf8 => cast_view_to_byte::<StringViewType, GenericStringType<i32>>(array),
1346            LargeUtf8 => cast_view_to_byte::<StringViewType, GenericStringType<i64>>(array),
1347            Time32(TimeUnit::Second) => parse_string_view::<Time32SecondType>(array, cast_options),
1348            Time32(TimeUnit::Millisecond) => {
1349                parse_string_view::<Time32MillisecondType>(array, cast_options)
1350            }
1351            Time64(TimeUnit::Microsecond) => {
1352                parse_string_view::<Time64MicrosecondType>(array, cast_options)
1353            }
1354            Time64(TimeUnit::Nanosecond) => {
1355                parse_string_view::<Time64NanosecondType>(array, cast_options)
1356            }
1357            Timestamp(TimeUnit::Second, to_tz) => {
1358                cast_view_to_timestamp::<TimestampSecondType>(array, to_tz.as_ref(), cast_options)
1359            }
1360            Timestamp(TimeUnit::Millisecond, to_tz) => cast_view_to_timestamp::<
1361                TimestampMillisecondType,
1362            >(
1363                array, to_tz.as_ref(), cast_options
1364            ),
1365            Timestamp(TimeUnit::Microsecond, to_tz) => cast_view_to_timestamp::<
1366                TimestampMicrosecondType,
1367            >(
1368                array, to_tz.as_ref(), cast_options
1369            ),
1370            Timestamp(TimeUnit::Nanosecond, to_tz) => cast_view_to_timestamp::<
1371                TimestampNanosecondType,
1372            >(
1373                array, to_tz.as_ref(), cast_options
1374            ),
1375            Interval(IntervalUnit::YearMonth) => {
1376                cast_view_to_year_month_interval(array, cast_options)
1377            }
1378            Interval(IntervalUnit::DayTime) => cast_view_to_day_time_interval(array, cast_options),
1379            Interval(IntervalUnit::MonthDayNano) => {
1380                cast_view_to_month_day_nano_interval(array, cast_options)
1381            }
1382            _ => Err(ArrowError::CastError(format!(
1383                "Casting from {from_type} to {to_type} not supported",
1384            ))),
1385        },
1386        (LargeUtf8, _) => match to_type {
1387            UInt8 => parse_string::<UInt8Type, i64>(array, cast_options),
1388            UInt16 => parse_string::<UInt16Type, i64>(array, cast_options),
1389            UInt32 => parse_string::<UInt32Type, i64>(array, cast_options),
1390            UInt64 => parse_string::<UInt64Type, i64>(array, cast_options),
1391            Int8 => parse_string::<Int8Type, i64>(array, cast_options),
1392            Int16 => parse_string::<Int16Type, i64>(array, cast_options),
1393            Int32 => parse_string::<Int32Type, i64>(array, cast_options),
1394            Int64 => parse_string::<Int64Type, i64>(array, cast_options),
1395            Float16 => parse_string::<Float16Type, i64>(array, cast_options),
1396            Float32 => parse_string::<Float32Type, i64>(array, cast_options),
1397            Float64 => parse_string::<Float64Type, i64>(array, cast_options),
1398            Date32 => parse_string::<Date32Type, i64>(array, cast_options),
1399            Date64 => parse_string::<Date64Type, i64>(array, cast_options),
1400            Utf8 => cast_byte_container::<LargeUtf8Type, Utf8Type>(array),
1401            Binary => {
1402                let large_binary = LargeBinaryArray::from(array.as_string::<i64>().clone());
1403                cast_byte_container::<LargeBinaryType, BinaryType>(&large_binary)
1404            }
1405            LargeBinary => Ok(Arc::new(LargeBinaryArray::from(
1406                array.as_string::<i64>().clone(),
1407            ))),
1408            Utf8View => Ok(Arc::new(StringViewArray::from(array.as_string::<i64>()))),
1409            BinaryView => Ok(Arc::new(BinaryViewArray::from(
1410                array
1411                    .as_string::<i64>()
1412                    .into_iter()
1413                    .map(|x| x.map(|x| x.as_bytes()))
1414                    .collect::<Vec<_>>(),
1415            ))),
1416            Time32(TimeUnit::Second) => parse_string::<Time32SecondType, i64>(array, cast_options),
1417            Time32(TimeUnit::Millisecond) => {
1418                parse_string::<Time32MillisecondType, i64>(array, cast_options)
1419            }
1420            Time64(TimeUnit::Microsecond) => {
1421                parse_string::<Time64MicrosecondType, i64>(array, cast_options)
1422            }
1423            Time64(TimeUnit::Nanosecond) => {
1424                parse_string::<Time64NanosecondType, i64>(array, cast_options)
1425            }
1426            Timestamp(TimeUnit::Second, to_tz) => cast_string_to_timestamp::<
1427                i64,
1428                TimestampSecondType,
1429            >(array, to_tz.as_ref(), cast_options),
1430            Timestamp(TimeUnit::Millisecond, to_tz) => cast_string_to_timestamp::<
1431                i64,
1432                TimestampMillisecondType,
1433            >(
1434                array, to_tz.as_ref(), cast_options
1435            ),
1436            Timestamp(TimeUnit::Microsecond, to_tz) => cast_string_to_timestamp::<
1437                i64,
1438                TimestampMicrosecondType,
1439            >(
1440                array, to_tz.as_ref(), cast_options
1441            ),
1442            Timestamp(TimeUnit::Nanosecond, to_tz) => cast_string_to_timestamp::<
1443                i64,
1444                TimestampNanosecondType,
1445            >(
1446                array, to_tz.as_ref(), cast_options
1447            ),
1448            Interval(IntervalUnit::YearMonth) => {
1449                cast_string_to_year_month_interval::<i64>(array, cast_options)
1450            }
1451            Interval(IntervalUnit::DayTime) => {
1452                cast_string_to_day_time_interval::<i64>(array, cast_options)
1453            }
1454            Interval(IntervalUnit::MonthDayNano) => {
1455                cast_string_to_month_day_nano_interval::<i64>(array, cast_options)
1456            }
1457            _ => Err(ArrowError::CastError(format!(
1458                "Casting from {from_type} to {to_type} not supported",
1459            ))),
1460        },
1461        (Binary, _) => match to_type {
1462            Utf8 => cast_binary_to_string::<i32>(array, cast_options),
1463            LargeUtf8 => {
1464                let array = cast_binary_to_string::<i32>(array, cast_options)?;
1465                cast_byte_container::<Utf8Type, LargeUtf8Type>(array.as_ref())
1466            }
1467            LargeBinary => cast_byte_container::<BinaryType, LargeBinaryType>(array),
1468            FixedSizeBinary(size) => {
1469                cast_binary_to_fixed_size_binary::<i32>(array, *size, cast_options)
1470            }
1471            BinaryView => Ok(Arc::new(BinaryViewArray::from(array.as_binary::<i32>()))),
1472            Utf8View => Ok(Arc::new(StringViewArray::from(
1473                cast_binary_to_string::<i32>(array, cast_options)?.as_string::<i32>(),
1474            ))),
1475            _ => Err(ArrowError::CastError(format!(
1476                "Casting from {from_type} to {to_type} not supported",
1477            ))),
1478        },
1479        (LargeBinary, _) => match to_type {
1480            Utf8 => {
1481                let array = cast_binary_to_string::<i64>(array, cast_options)?;
1482                cast_byte_container::<LargeUtf8Type, Utf8Type>(array.as_ref())
1483            }
1484            LargeUtf8 => cast_binary_to_string::<i64>(array, cast_options),
1485            Binary => cast_byte_container::<LargeBinaryType, BinaryType>(array),
1486            FixedSizeBinary(size) => {
1487                cast_binary_to_fixed_size_binary::<i64>(array, *size, cast_options)
1488            }
1489            BinaryView => Ok(Arc::new(BinaryViewArray::from(array.as_binary::<i64>()))),
1490            Utf8View => {
1491                let array = cast_binary_to_string::<i64>(array, cast_options)?;
1492                Ok(Arc::new(StringViewArray::from(array.as_string::<i64>())))
1493            }
1494            _ => Err(ArrowError::CastError(format!(
1495                "Casting from {from_type} to {to_type} not supported",
1496            ))),
1497        },
1498        (FixedSizeBinary(size), _) => match to_type {
1499            Binary => cast_fixed_size_binary_to_binary::<i32>(array, *size),
1500            LargeBinary => cast_fixed_size_binary_to_binary::<i64>(array, *size),
1501            BinaryView => cast_fixed_size_binary_to_binary_view(array, *size),
1502            _ => Err(ArrowError::CastError(format!(
1503                "Casting from {from_type} to {to_type} not supported",
1504            ))),
1505        },
1506        (BinaryView, Binary) => cast_view_to_byte::<BinaryViewType, GenericBinaryType<i32>>(array),
1507        (BinaryView, LargeBinary) => {
1508            cast_view_to_byte::<BinaryViewType, GenericBinaryType<i64>>(array)
1509        }
1510        (BinaryView, Utf8) => {
1511            let binary_arr = cast_view_to_byte::<BinaryViewType, GenericBinaryType<i32>>(array)?;
1512            cast_binary_to_string::<i32>(&binary_arr, cast_options)
1513        }
1514        (BinaryView, LargeUtf8) => {
1515            let binary_arr = cast_view_to_byte::<BinaryViewType, GenericBinaryType<i64>>(array)?;
1516            cast_binary_to_string::<i64>(&binary_arr, cast_options)
1517        }
1518        (BinaryView, Utf8View) => cast_binary_view_to_string_view(array, cast_options),
1519        (BinaryView, _) => Err(ArrowError::CastError(format!(
1520            "Casting from {from_type} to {to_type} not supported",
1521        ))),
1522        (from_type, Utf8View) if from_type.is_primitive() => {
1523            value_to_string_view(array, cast_options)
1524        }
1525        (from_type, LargeUtf8) if from_type.is_primitive() => {
1526            value_to_string::<i64>(array, cast_options)
1527        }
1528        (from_type, Utf8) if from_type.is_primitive() => {
1529            value_to_string::<i32>(array, cast_options)
1530        }
1531        (from_type, Binary) if from_type.is_integer() => match from_type {
1532            UInt8 => cast_numeric_to_binary::<UInt8Type, i32>(array),
1533            UInt16 => cast_numeric_to_binary::<UInt16Type, i32>(array),
1534            UInt32 => cast_numeric_to_binary::<UInt32Type, i32>(array),
1535            UInt64 => cast_numeric_to_binary::<UInt64Type, i32>(array),
1536            Int8 => cast_numeric_to_binary::<Int8Type, i32>(array),
1537            Int16 => cast_numeric_to_binary::<Int16Type, i32>(array),
1538            Int32 => cast_numeric_to_binary::<Int32Type, i32>(array),
1539            Int64 => cast_numeric_to_binary::<Int64Type, i32>(array),
1540            _ => unreachable!(),
1541        },
1542        (from_type, LargeBinary) if from_type.is_integer() => match from_type {
1543            UInt8 => cast_numeric_to_binary::<UInt8Type, i64>(array),
1544            UInt16 => cast_numeric_to_binary::<UInt16Type, i64>(array),
1545            UInt32 => cast_numeric_to_binary::<UInt32Type, i64>(array),
1546            UInt64 => cast_numeric_to_binary::<UInt64Type, i64>(array),
1547            Int8 => cast_numeric_to_binary::<Int8Type, i64>(array),
1548            Int16 => cast_numeric_to_binary::<Int16Type, i64>(array),
1549            Int32 => cast_numeric_to_binary::<Int32Type, i64>(array),
1550            Int64 => cast_numeric_to_binary::<Int64Type, i64>(array),
1551            _ => unreachable!(),
1552        },
1553        // start numeric casts
1554        (UInt8, UInt16) => cast_numeric_arrays::<UInt8Type, UInt16Type>(array, cast_options),
1555        (UInt8, UInt32) => cast_numeric_arrays::<UInt8Type, UInt32Type>(array, cast_options),
1556        (UInt8, UInt64) => cast_numeric_arrays::<UInt8Type, UInt64Type>(array, cast_options),
1557        (UInt8, Int8) => cast_numeric_arrays::<UInt8Type, Int8Type>(array, cast_options),
1558        (UInt8, Int16) => cast_numeric_arrays::<UInt8Type, Int16Type>(array, cast_options),
1559        (UInt8, Int32) => cast_numeric_arrays::<UInt8Type, Int32Type>(array, cast_options),
1560        (UInt8, Int64) => cast_numeric_arrays::<UInt8Type, Int64Type>(array, cast_options),
1561        (UInt8, Float16) => cast_numeric_arrays::<UInt8Type, Float16Type>(array, cast_options),
1562        (UInt8, Float32) => cast_numeric_arrays::<UInt8Type, Float32Type>(array, cast_options),
1563        (UInt8, Float64) => cast_numeric_arrays::<UInt8Type, Float64Type>(array, cast_options),
1564
1565        (UInt16, UInt8) => cast_numeric_arrays::<UInt16Type, UInt8Type>(array, cast_options),
1566        (UInt16, UInt32) => cast_numeric_arrays::<UInt16Type, UInt32Type>(array, cast_options),
1567        (UInt16, UInt64) => cast_numeric_arrays::<UInt16Type, UInt64Type>(array, cast_options),
1568        (UInt16, Int8) => cast_numeric_arrays::<UInt16Type, Int8Type>(array, cast_options),
1569        (UInt16, Int16) => cast_numeric_arrays::<UInt16Type, Int16Type>(array, cast_options),
1570        (UInt16, Int32) => cast_numeric_arrays::<UInt16Type, Int32Type>(array, cast_options),
1571        (UInt16, Int64) => cast_numeric_arrays::<UInt16Type, Int64Type>(array, cast_options),
1572        (UInt16, Float16) => cast_numeric_arrays::<UInt16Type, Float16Type>(array, cast_options),
1573        (UInt16, Float32) => cast_numeric_arrays::<UInt16Type, Float32Type>(array, cast_options),
1574        (UInt16, Float64) => cast_numeric_arrays::<UInt16Type, Float64Type>(array, cast_options),
1575
1576        (UInt32, UInt8) => cast_numeric_arrays::<UInt32Type, UInt8Type>(array, cast_options),
1577        (UInt32, UInt16) => cast_numeric_arrays::<UInt32Type, UInt16Type>(array, cast_options),
1578        (UInt32, UInt64) => cast_numeric_arrays::<UInt32Type, UInt64Type>(array, cast_options),
1579        (UInt32, Int8) => cast_numeric_arrays::<UInt32Type, Int8Type>(array, cast_options),
1580        (UInt32, Int16) => cast_numeric_arrays::<UInt32Type, Int16Type>(array, cast_options),
1581        (UInt32, Int32) => cast_numeric_arrays::<UInt32Type, Int32Type>(array, cast_options),
1582        (UInt32, Int64) => cast_numeric_arrays::<UInt32Type, Int64Type>(array, cast_options),
1583        (UInt32, Float16) => cast_numeric_arrays::<UInt32Type, Float16Type>(array, cast_options),
1584        (UInt32, Float32) => cast_numeric_arrays::<UInt32Type, Float32Type>(array, cast_options),
1585        (UInt32, Float64) => cast_numeric_arrays::<UInt32Type, Float64Type>(array, cast_options),
1586
1587        (UInt64, UInt8) => cast_numeric_arrays::<UInt64Type, UInt8Type>(array, cast_options),
1588        (UInt64, UInt16) => cast_numeric_arrays::<UInt64Type, UInt16Type>(array, cast_options),
1589        (UInt64, UInt32) => cast_numeric_arrays::<UInt64Type, UInt32Type>(array, cast_options),
1590        (UInt64, Int8) => cast_numeric_arrays::<UInt64Type, Int8Type>(array, cast_options),
1591        (UInt64, Int16) => cast_numeric_arrays::<UInt64Type, Int16Type>(array, cast_options),
1592        (UInt64, Int32) => cast_numeric_arrays::<UInt64Type, Int32Type>(array, cast_options),
1593        (UInt64, Int64) => cast_numeric_arrays::<UInt64Type, Int64Type>(array, cast_options),
1594        (UInt64, Float16) => cast_numeric_arrays::<UInt64Type, Float16Type>(array, cast_options),
1595        (UInt64, Float32) => cast_numeric_arrays::<UInt64Type, Float32Type>(array, cast_options),
1596        (UInt64, Float64) => cast_numeric_arrays::<UInt64Type, Float64Type>(array, cast_options),
1597
1598        (Int8, UInt8) => cast_numeric_arrays::<Int8Type, UInt8Type>(array, cast_options),
1599        (Int8, UInt16) => cast_numeric_arrays::<Int8Type, UInt16Type>(array, cast_options),
1600        (Int8, UInt32) => cast_numeric_arrays::<Int8Type, UInt32Type>(array, cast_options),
1601        (Int8, UInt64) => cast_numeric_arrays::<Int8Type, UInt64Type>(array, cast_options),
1602        (Int8, Int16) => cast_numeric_arrays::<Int8Type, Int16Type>(array, cast_options),
1603        (Int8, Int32) => cast_numeric_arrays::<Int8Type, Int32Type>(array, cast_options),
1604        (Int8, Int64) => cast_numeric_arrays::<Int8Type, Int64Type>(array, cast_options),
1605        (Int8, Float16) => cast_numeric_arrays::<Int8Type, Float16Type>(array, cast_options),
1606        (Int8, Float32) => cast_numeric_arrays::<Int8Type, Float32Type>(array, cast_options),
1607        (Int8, Float64) => cast_numeric_arrays::<Int8Type, Float64Type>(array, cast_options),
1608
1609        (Int16, UInt8) => cast_numeric_arrays::<Int16Type, UInt8Type>(array, cast_options),
1610        (Int16, UInt16) => cast_numeric_arrays::<Int16Type, UInt16Type>(array, cast_options),
1611        (Int16, UInt32) => cast_numeric_arrays::<Int16Type, UInt32Type>(array, cast_options),
1612        (Int16, UInt64) => cast_numeric_arrays::<Int16Type, UInt64Type>(array, cast_options),
1613        (Int16, Int8) => cast_numeric_arrays::<Int16Type, Int8Type>(array, cast_options),
1614        (Int16, Int32) => cast_numeric_arrays::<Int16Type, Int32Type>(array, cast_options),
1615        (Int16, Int64) => cast_numeric_arrays::<Int16Type, Int64Type>(array, cast_options),
1616        (Int16, Float16) => cast_numeric_arrays::<Int16Type, Float16Type>(array, cast_options),
1617        (Int16, Float32) => cast_numeric_arrays::<Int16Type, Float32Type>(array, cast_options),
1618        (Int16, Float64) => cast_numeric_arrays::<Int16Type, Float64Type>(array, cast_options),
1619
1620        (Int32, UInt8) => cast_numeric_arrays::<Int32Type, UInt8Type>(array, cast_options),
1621        (Int32, UInt16) => cast_numeric_arrays::<Int32Type, UInt16Type>(array, cast_options),
1622        (Int32, UInt32) => cast_numeric_arrays::<Int32Type, UInt32Type>(array, cast_options),
1623        (Int32, UInt64) => cast_numeric_arrays::<Int32Type, UInt64Type>(array, cast_options),
1624        (Int32, Int8) => cast_numeric_arrays::<Int32Type, Int8Type>(array, cast_options),
1625        (Int32, Int16) => cast_numeric_arrays::<Int32Type, Int16Type>(array, cast_options),
1626        (Int32, Int64) => cast_numeric_arrays::<Int32Type, Int64Type>(array, cast_options),
1627        (Int32, Float16) => cast_numeric_arrays::<Int32Type, Float16Type>(array, cast_options),
1628        (Int32, Float32) => cast_numeric_arrays::<Int32Type, Float32Type>(array, cast_options),
1629        (Int32, Float64) => cast_numeric_arrays::<Int32Type, Float64Type>(array, cast_options),
1630
1631        (Int64, UInt8) => cast_numeric_arrays::<Int64Type, UInt8Type>(array, cast_options),
1632        (Int64, UInt16) => cast_numeric_arrays::<Int64Type, UInt16Type>(array, cast_options),
1633        (Int64, UInt32) => cast_numeric_arrays::<Int64Type, UInt32Type>(array, cast_options),
1634        (Int64, UInt64) => cast_numeric_arrays::<Int64Type, UInt64Type>(array, cast_options),
1635        (Int64, Int8) => cast_numeric_arrays::<Int64Type, Int8Type>(array, cast_options),
1636        (Int64, Int16) => cast_numeric_arrays::<Int64Type, Int16Type>(array, cast_options),
1637        (Int64, Int32) => cast_numeric_arrays::<Int64Type, Int32Type>(array, cast_options),
1638        (Int64, Float16) => cast_numeric_arrays::<Int64Type, Float16Type>(array, cast_options),
1639        (Int64, Float32) => cast_numeric_arrays::<Int64Type, Float32Type>(array, cast_options),
1640        (Int64, Float64) => cast_numeric_arrays::<Int64Type, Float64Type>(array, cast_options),
1641
1642        (Float16, UInt8) => cast_numeric_arrays::<Float16Type, UInt8Type>(array, cast_options),
1643        (Float16, UInt16) => cast_numeric_arrays::<Float16Type, UInt16Type>(array, cast_options),
1644        (Float16, UInt32) => cast_numeric_arrays::<Float16Type, UInt32Type>(array, cast_options),
1645        (Float16, UInt64) => cast_numeric_arrays::<Float16Type, UInt64Type>(array, cast_options),
1646        (Float16, Int8) => cast_numeric_arrays::<Float16Type, Int8Type>(array, cast_options),
1647        (Float16, Int16) => cast_numeric_arrays::<Float16Type, Int16Type>(array, cast_options),
1648        (Float16, Int32) => cast_numeric_arrays::<Float16Type, Int32Type>(array, cast_options),
1649        (Float16, Int64) => cast_numeric_arrays::<Float16Type, Int64Type>(array, cast_options),
1650        (Float16, Float32) => cast_numeric_arrays::<Float16Type, Float32Type>(array, cast_options),
1651        (Float16, Float64) => cast_numeric_arrays::<Float16Type, Float64Type>(array, cast_options),
1652
1653        (Float32, UInt8) => cast_numeric_arrays::<Float32Type, UInt8Type>(array, cast_options),
1654        (Float32, UInt16) => cast_numeric_arrays::<Float32Type, UInt16Type>(array, cast_options),
1655        (Float32, UInt32) => cast_numeric_arrays::<Float32Type, UInt32Type>(array, cast_options),
1656        (Float32, UInt64) => cast_numeric_arrays::<Float32Type, UInt64Type>(array, cast_options),
1657        (Float32, Int8) => cast_numeric_arrays::<Float32Type, Int8Type>(array, cast_options),
1658        (Float32, Int16) => cast_numeric_arrays::<Float32Type, Int16Type>(array, cast_options),
1659        (Float32, Int32) => cast_numeric_arrays::<Float32Type, Int32Type>(array, cast_options),
1660        (Float32, Int64) => cast_numeric_arrays::<Float32Type, Int64Type>(array, cast_options),
1661        (Float32, Float16) => cast_numeric_arrays::<Float32Type, Float16Type>(array, cast_options),
1662        (Float32, Float64) => cast_numeric_arrays::<Float32Type, Float64Type>(array, cast_options),
1663
1664        (Float64, UInt8) => cast_numeric_arrays::<Float64Type, UInt8Type>(array, cast_options),
1665        (Float64, UInt16) => cast_numeric_arrays::<Float64Type, UInt16Type>(array, cast_options),
1666        (Float64, UInt32) => cast_numeric_arrays::<Float64Type, UInt32Type>(array, cast_options),
1667        (Float64, UInt64) => cast_numeric_arrays::<Float64Type, UInt64Type>(array, cast_options),
1668        (Float64, Int8) => cast_numeric_arrays::<Float64Type, Int8Type>(array, cast_options),
1669        (Float64, Int16) => cast_numeric_arrays::<Float64Type, Int16Type>(array, cast_options),
1670        (Float64, Int32) => cast_numeric_arrays::<Float64Type, Int32Type>(array, cast_options),
1671        (Float64, Int64) => cast_numeric_arrays::<Float64Type, Int64Type>(array, cast_options),
1672        (Float64, Float16) => cast_numeric_arrays::<Float64Type, Float16Type>(array, cast_options),
1673        (Float64, Float32) => cast_numeric_arrays::<Float64Type, Float32Type>(array, cast_options),
1674        // end numeric casts
1675
1676        // temporal casts
1677        (Int32, Date32) => cast_reinterpret_arrays::<Int32Type, Date32Type>(array),
1678        (Int32, Date64) => cast_with_options(
1679            &cast_with_options(array, &Date32, cast_options)?,
1680            &Date64,
1681            cast_options,
1682        ),
1683        (Int32, Time32(TimeUnit::Second)) => {
1684            cast_reinterpret_arrays::<Int32Type, Time32SecondType>(array)
1685        }
1686        (Int32, Time32(TimeUnit::Millisecond)) => {
1687            cast_reinterpret_arrays::<Int32Type, Time32MillisecondType>(array)
1688        }
1689        // No support for microsecond/nanosecond with i32
1690        (Date32, Int32) => cast_reinterpret_arrays::<Date32Type, Int32Type>(array),
1691        (Date32, Int64) => cast_with_options(
1692            &cast_with_options(array, &Int32, cast_options)?,
1693            &Int64,
1694            cast_options,
1695        ),
1696        (Time32(TimeUnit::Second), Int32) => {
1697            cast_reinterpret_arrays::<Time32SecondType, Int32Type>(array)
1698        }
1699        (Time32(TimeUnit::Millisecond), Int32) => {
1700            cast_reinterpret_arrays::<Time32MillisecondType, Int32Type>(array)
1701        }
1702        (Time32(TimeUnit::Second), Int64) => cast_with_options(
1703            &cast_with_options(array, &Int32, cast_options)?,
1704            &Int64,
1705            cast_options,
1706        ),
1707        (Time32(TimeUnit::Millisecond), Int64) => cast_with_options(
1708            &cast_with_options(array, &Int32, cast_options)?,
1709            &Int64,
1710            cast_options,
1711        ),
1712        (Int64, Date64) => cast_reinterpret_arrays::<Int64Type, Date64Type>(array),
1713        (Int64, Date32) => cast_with_options(
1714            &cast_with_options(array, &Int32, cast_options)?,
1715            &Date32,
1716            cast_options,
1717        ),
1718        // No support for second/milliseconds with i64
1719        (Int64, Time64(TimeUnit::Microsecond)) => {
1720            cast_reinterpret_arrays::<Int64Type, Time64MicrosecondType>(array)
1721        }
1722        (Int64, Time64(TimeUnit::Nanosecond)) => {
1723            cast_reinterpret_arrays::<Int64Type, Time64NanosecondType>(array)
1724        }
1725
1726        (Date64, Int64) => cast_reinterpret_arrays::<Date64Type, Int64Type>(array),
1727        (Date64, Int32) => cast_with_options(
1728            &cast_with_options(array, &Int64, cast_options)?,
1729            &Int32,
1730            cast_options,
1731        ),
1732        (Time64(TimeUnit::Microsecond), Int64) => {
1733            cast_reinterpret_arrays::<Time64MicrosecondType, Int64Type>(array)
1734        }
1735        (Time64(TimeUnit::Nanosecond), Int64) => {
1736            cast_reinterpret_arrays::<Time64NanosecondType, Int64Type>(array)
1737        }
1738        (Date32, Date64) => Ok(Arc::new(
1739            array
1740                .as_primitive::<Date32Type>()
1741                .unary::<_, Date64Type>(|x| x as i64 * MILLISECONDS_IN_DAY),
1742        )),
1743        (Date64, Date32) => {
1744            let array = array.as_primitive::<Date64Type>();
1745            let result = if cast_options.safe {
1746                array.unary_opt::<_, Date32Type>(|x| i32::try_from(x / MILLISECONDS_IN_DAY).ok())
1747            } else {
1748                array.try_unary::<_, Date32Type, _>(|x| {
1749                    i32::try_from(x / MILLISECONDS_IN_DAY).map_err(|_| {
1750                        ArrowError::CastError(format!(
1751                            "Cannot cast Date64 value {x} to Date32 without overflow"
1752                        ))
1753                    })
1754                })?
1755            };
1756            Ok(Arc::new(result))
1757        }
1758
1759        (Time32(TimeUnit::Second), Time32(TimeUnit::Millisecond)) => {
1760            let array = array.as_primitive::<Time32SecondType>();
1761            let result = if cast_options.safe {
1762                array.unary_opt::<_, Time32MillisecondType>(|x| x.checked_mul(MILLISECONDS as i32))
1763            } else {
1764                array.try_unary::<_, Time32MillisecondType, _>(|x| {
1765                    x.mul_checked(MILLISECONDS as i32)
1766                })?
1767            };
1768            Ok(Arc::new(result))
1769        }
1770        (Time32(TimeUnit::Second), Time64(TimeUnit::Microsecond)) => Ok(Arc::new(
1771            array
1772                .as_primitive::<Time32SecondType>()
1773                .unary::<_, Time64MicrosecondType>(|x| x as i64 * MICROSECONDS),
1774        )),
1775        (Time32(TimeUnit::Second), Time64(TimeUnit::Nanosecond)) => Ok(Arc::new(
1776            array
1777                .as_primitive::<Time32SecondType>()
1778                .unary::<_, Time64NanosecondType>(|x| x as i64 * NANOSECONDS),
1779        )),
1780
1781        (Time32(TimeUnit::Millisecond), Time32(TimeUnit::Second)) => Ok(Arc::new(
1782            array
1783                .as_primitive::<Time32MillisecondType>()
1784                .unary::<_, Time32SecondType>(|x| x / MILLISECONDS as i32),
1785        )),
1786        (Time32(TimeUnit::Millisecond), Time64(TimeUnit::Microsecond)) => Ok(Arc::new(
1787            array
1788                .as_primitive::<Time32MillisecondType>()
1789                .unary::<_, Time64MicrosecondType>(|x| x as i64 * (MICROSECONDS / MILLISECONDS)),
1790        )),
1791        (Time32(TimeUnit::Millisecond), Time64(TimeUnit::Nanosecond)) => Ok(Arc::new(
1792            array
1793                .as_primitive::<Time32MillisecondType>()
1794                .unary::<_, Time64NanosecondType>(|x| x as i64 * (NANOSECONDS / MILLISECONDS)),
1795        )),
1796
1797        (Time64(TimeUnit::Microsecond), Time32(TimeUnit::Second)) => {
1798            cast_time64_to_time32::<Time64MicrosecondType, Time32SecondType>(
1799                array,
1800                MICROSECONDS,
1801                cast_options,
1802            )
1803        }
1804        (Time64(TimeUnit::Microsecond), Time32(TimeUnit::Millisecond)) => {
1805            cast_time64_to_time32::<Time64MicrosecondType, Time32MillisecondType>(
1806                array,
1807                MICROSECONDS / MILLISECONDS,
1808                cast_options,
1809            )
1810        }
1811        (Time64(TimeUnit::Microsecond), Time64(TimeUnit::Nanosecond)) => {
1812            let array = array.as_primitive::<Time64MicrosecondType>();
1813            let result = if cast_options.safe {
1814                array.unary_opt::<_, Time64NanosecondType>(|x| {
1815                    x.checked_mul(NANOSECONDS / MICROSECONDS)
1816                })
1817            } else {
1818                array.try_unary::<_, Time64NanosecondType, _>(|x| {
1819                    x.mul_checked(NANOSECONDS / MICROSECONDS)
1820                })?
1821            };
1822            Ok(Arc::new(result))
1823        }
1824
1825        (Time64(TimeUnit::Nanosecond), Time32(TimeUnit::Second)) => {
1826            cast_time64_to_time32::<Time64NanosecondType, Time32SecondType>(
1827                array,
1828                NANOSECONDS,
1829                cast_options,
1830            )
1831        }
1832        (Time64(TimeUnit::Nanosecond), Time32(TimeUnit::Millisecond)) => {
1833            cast_time64_to_time32::<Time64NanosecondType, Time32MillisecondType>(
1834                array,
1835                NANOSECONDS / MILLISECONDS,
1836                cast_options,
1837            )
1838        }
1839        (Time64(TimeUnit::Nanosecond), Time64(TimeUnit::Microsecond)) => Ok(Arc::new(
1840            array
1841                .as_primitive::<Time64NanosecondType>()
1842                .unary::<_, Time64MicrosecondType>(|x| x / (NANOSECONDS / MICROSECONDS)),
1843        )),
1844
1845        // Timestamp to integer/floating/decimals
1846        (Timestamp(TimeUnit::Second, _), _) if to_type.is_numeric() => {
1847            let array = cast_reinterpret_arrays::<TimestampSecondType, Int64Type>(array)?;
1848            cast_with_options(&array, to_type, cast_options)
1849        }
1850        (Timestamp(TimeUnit::Millisecond, _), _) if to_type.is_numeric() => {
1851            let array = cast_reinterpret_arrays::<TimestampMillisecondType, Int64Type>(array)?;
1852            cast_with_options(&array, to_type, cast_options)
1853        }
1854        (Timestamp(TimeUnit::Microsecond, _), _) if to_type.is_numeric() => {
1855            let array = cast_reinterpret_arrays::<TimestampMicrosecondType, Int64Type>(array)?;
1856            cast_with_options(&array, to_type, cast_options)
1857        }
1858        (Timestamp(TimeUnit::Nanosecond, _), _) if to_type.is_numeric() => {
1859            let array = cast_reinterpret_arrays::<TimestampNanosecondType, Int64Type>(array)?;
1860            cast_with_options(&array, to_type, cast_options)
1861        }
1862
1863        (_, Timestamp(unit, tz)) if from_type.is_numeric() => {
1864            let array = cast_with_options(array, &Int64, cast_options)?;
1865            Ok(make_timestamp_array(
1866                array.as_primitive(),
1867                *unit,
1868                tz.clone(),
1869            ))
1870        }
1871
1872        (Timestamp(from_unit, from_tz), Timestamp(to_unit, to_tz)) => {
1873            let array = cast_with_options(array, &Int64, cast_options)?;
1874            let time_array = array.as_primitive::<Int64Type>();
1875            let from_size = time_unit_multiple(from_unit);
1876            let to_size = time_unit_multiple(to_unit);
1877            // we either divide or multiply, depending on size of each unit
1878            // units are never the same when the types are the same
1879            let converted = match from_size.cmp(&to_size) {
1880                Ordering::Greater => {
1881                    let divisor = from_size / to_size;
1882                    time_array.unary::<_, Int64Type>(|o| o / divisor)
1883                }
1884                Ordering::Equal => time_array.clone(),
1885                Ordering::Less => {
1886                    let mul = to_size / from_size;
1887                    if cast_options.safe {
1888                        time_array.unary_opt::<_, Int64Type>(|o| o.checked_mul(mul))
1889                    } else {
1890                        time_array.try_unary::<_, Int64Type, _>(|o| o.mul_checked(mul))?
1891                    }
1892                }
1893            };
1894            // Normalize timezone
1895            let adjusted = match (from_tz, to_tz) {
1896                // Only this case needs to be adjusted because we're casting from
1897                // unknown time offset to some time offset, we want the time to be
1898                // unchanged.
1899                //
1900                // i.e. Timestamp('2001-01-01T00:00', None) -> Timestamp('2001-01-01T00:00', '+0700')
1901                //
1902                // For IANA timezones a wall clock reading is not always a unique
1903                // instant: a "fall back" DST transition makes an hour occur twice
1904                // and a "spring forward" transition skips an hour entirely. See
1905                // `resolve_local_offset` for how those readings are resolved.
1906                (None, Some(to_tz)) => {
1907                    let to_tz: Tz = to_tz.parse()?;
1908                    match to_unit {
1909                        TimeUnit::Second => adjust_timestamp_to_timezone::<TimestampSecondType>(
1910                            converted,
1911                            &to_tz,
1912                            cast_options,
1913                        )?,
1914                        TimeUnit::Millisecond => adjust_timestamp_to_timezone::<
1915                            TimestampMillisecondType,
1916                        >(
1917                            converted, &to_tz, cast_options
1918                        )?,
1919                        TimeUnit::Microsecond => adjust_timestamp_to_timezone::<
1920                            TimestampMicrosecondType,
1921                        >(
1922                            converted, &to_tz, cast_options
1923                        )?,
1924                        TimeUnit::Nanosecond => adjust_timestamp_to_timezone::<
1925                            TimestampNanosecondType,
1926                        >(
1927                            converted, &to_tz, cast_options
1928                        )?,
1929                    }
1930                }
1931                _ => converted,
1932            };
1933            Ok(make_timestamp_array(&adjusted, *to_unit, to_tz.clone()))
1934        }
1935        (Timestamp(TimeUnit::Microsecond, _), Date32) => timestamp_to_date32(
1936            array.as_primitive::<TimestampMicrosecondType>(),
1937            cast_options,
1938        ),
1939        (Timestamp(TimeUnit::Millisecond, _), Date32) => timestamp_to_date32(
1940            array.as_primitive::<TimestampMillisecondType>(),
1941            cast_options,
1942        ),
1943        (Timestamp(TimeUnit::Second, _), Date32) => {
1944            timestamp_to_date32(array.as_primitive::<TimestampSecondType>(), cast_options)
1945        }
1946        (Timestamp(TimeUnit::Nanosecond, _), Date32) => timestamp_to_date32(
1947            array.as_primitive::<TimestampNanosecondType>(),
1948            cast_options,
1949        ),
1950        (Timestamp(TimeUnit::Second, _), Date64) => {
1951            timestamp_to_date64(array.as_primitive::<TimestampSecondType>(), cast_options)
1952        }
1953        (Timestamp(TimeUnit::Millisecond, _), Date64) => timestamp_to_date64(
1954            array.as_primitive::<TimestampMillisecondType>(),
1955            cast_options,
1956        ),
1957        (Timestamp(TimeUnit::Microsecond, _), Date64) => timestamp_to_date64(
1958            array.as_primitive::<TimestampMicrosecondType>(),
1959            cast_options,
1960        ),
1961        (Timestamp(TimeUnit::Nanosecond, _), Date64) => timestamp_to_date64(
1962            array.as_primitive::<TimestampNanosecondType>(),
1963            cast_options,
1964        ),
1965        (Timestamp(TimeUnit::Second, _), Time32(_) | Time64(_)) => {
1966            cast_timestamp_to_time::<TimestampSecondType>(array, to_type, cast_options)
1967        }
1968        (Timestamp(TimeUnit::Millisecond, _), Time32(_) | Time64(_)) => {
1969            cast_timestamp_to_time::<TimestampMillisecondType>(array, to_type, cast_options)
1970        }
1971        (Timestamp(TimeUnit::Microsecond, _), Time32(_) | Time64(_)) => {
1972            cast_timestamp_to_time::<TimestampMicrosecondType>(array, to_type, cast_options)
1973        }
1974        (Timestamp(TimeUnit::Nanosecond, _), Time32(_) | Time64(_)) => {
1975            cast_timestamp_to_time::<TimestampNanosecondType>(array, to_type, cast_options)
1976        }
1977        (Date64, Timestamp(TimeUnit::Second, _)) => {
1978            let array = array
1979                .as_primitive::<Date64Type>()
1980                .unary::<_, TimestampSecondType>(|x| x / MILLISECONDS);
1981
1982            cast_with_options(&array, to_type, cast_options)
1983        }
1984        (Date64, Timestamp(TimeUnit::Millisecond, _)) => {
1985            let array = array
1986                .as_primitive::<Date64Type>()
1987                .reinterpret_cast::<TimestampMillisecondType>();
1988
1989            cast_with_options(&array, to_type, cast_options)
1990        }
1991
1992        (Date64, Timestamp(TimeUnit::Microsecond, _)) => {
1993            let array = array
1994                .as_primitive::<Date64Type>()
1995                .reinterpret_cast::<TimestampMillisecondType>();
1996
1997            cast_with_options(&array, to_type, cast_options)
1998        }
1999        (Date64, Timestamp(TimeUnit::Nanosecond, _)) => {
2000            let array = array
2001                .as_primitive::<Date64Type>()
2002                .reinterpret_cast::<TimestampMillisecondType>();
2003
2004            cast_with_options(&array, to_type, cast_options)
2005        }
2006        (Date32, Timestamp(TimeUnit::Second, _)) => {
2007            let array = array
2008                .as_primitive::<Date32Type>()
2009                .unary::<_, TimestampSecondType>(|x| (x as i64) * SECONDS_IN_DAY);
2010
2011            cast_with_options(&array, to_type, cast_options)
2012        }
2013        (Date32, Timestamp(TimeUnit::Millisecond, _)) => {
2014            let array = array
2015                .as_primitive::<Date32Type>()
2016                .unary::<_, TimestampMillisecondType>(|x| (x as i64) * MILLISECONDS_IN_DAY);
2017
2018            cast_with_options(&array, to_type, cast_options)
2019        }
2020        (Date32, Timestamp(TimeUnit::Microsecond, _)) => {
2021            let date_array = array.as_primitive::<Date32Type>();
2022            let converted = if cast_options.safe {
2023                date_array.unary_opt::<_, TimestampMicrosecondType>(|x| {
2024                    (x as i64).checked_mul(MICROSECONDS_IN_DAY)
2025                })
2026            } else {
2027                date_array.try_unary::<_, TimestampMicrosecondType, _>(|x| {
2028                    (x as i64).mul_checked(MICROSECONDS_IN_DAY)
2029                })?
2030            };
2031            cast_with_options(&converted, to_type, cast_options)
2032        }
2033        (Date32, Timestamp(TimeUnit::Nanosecond, _)) => {
2034            let date_array = array.as_primitive::<Date32Type>();
2035            let converted = if cast_options.safe {
2036                date_array.unary_opt::<_, TimestampNanosecondType>(|x| {
2037                    (x as i64).checked_mul(NANOSECONDS_IN_DAY)
2038                })
2039            } else {
2040                date_array.try_unary::<_, TimestampNanosecondType, _>(|x| {
2041                    (x as i64).mul_checked(NANOSECONDS_IN_DAY)
2042                })?
2043            };
2044            cast_with_options(&converted, to_type, cast_options)
2045        }
2046
2047        (_, Duration(unit)) if from_type.is_numeric() => {
2048            let array = cast_with_options(array, &Int64, cast_options)?;
2049            Ok(make_duration_array(array.as_primitive(), *unit))
2050        }
2051        (Duration(TimeUnit::Second), _) if to_type.is_numeric() => {
2052            let array = cast_reinterpret_arrays::<DurationSecondType, Int64Type>(array)?;
2053            cast_with_options(&array, to_type, cast_options)
2054        }
2055        (Duration(TimeUnit::Millisecond), _) if to_type.is_numeric() => {
2056            let array = cast_reinterpret_arrays::<DurationMillisecondType, Int64Type>(array)?;
2057            cast_with_options(&array, to_type, cast_options)
2058        }
2059        (Duration(TimeUnit::Microsecond), _) if to_type.is_numeric() => {
2060            let array = cast_reinterpret_arrays::<DurationMicrosecondType, Int64Type>(array)?;
2061            cast_with_options(&array, to_type, cast_options)
2062        }
2063        (Duration(TimeUnit::Nanosecond), _) if to_type.is_numeric() => {
2064            let array = cast_reinterpret_arrays::<DurationNanosecondType, Int64Type>(array)?;
2065            cast_with_options(&array, to_type, cast_options)
2066        }
2067
2068        (Duration(from_unit), Duration(to_unit)) => {
2069            let array = cast_with_options(array, &Int64, cast_options)?;
2070            let time_array = array.as_primitive::<Int64Type>();
2071            let from_size = time_unit_multiple(from_unit);
2072            let to_size = time_unit_multiple(to_unit);
2073            // we either divide or multiply, depending on size of each unit
2074            // units are never the same when the types are the same
2075            let converted = match from_size.cmp(&to_size) {
2076                Ordering::Greater => {
2077                    let divisor = from_size / to_size;
2078                    time_array.unary::<_, Int64Type>(|o| o / divisor)
2079                }
2080                Ordering::Equal => time_array.clone(),
2081                Ordering::Less => {
2082                    let mul = to_size / from_size;
2083                    if cast_options.safe {
2084                        time_array.unary_opt::<_, Int64Type>(|o| o.checked_mul(mul))
2085                    } else {
2086                        time_array.try_unary::<_, Int64Type, _>(|o| o.mul_checked(mul))?
2087                    }
2088                }
2089            };
2090            Ok(make_duration_array(&converted, *to_unit))
2091        }
2092
2093        (Duration(TimeUnit::Second), Interval(IntervalUnit::MonthDayNano)) => {
2094            cast_duration_to_interval::<DurationSecondType>(array, cast_options)
2095        }
2096        (Duration(TimeUnit::Millisecond), Interval(IntervalUnit::MonthDayNano)) => {
2097            cast_duration_to_interval::<DurationMillisecondType>(array, cast_options)
2098        }
2099        (Duration(TimeUnit::Microsecond), Interval(IntervalUnit::MonthDayNano)) => {
2100            cast_duration_to_interval::<DurationMicrosecondType>(array, cast_options)
2101        }
2102        (Duration(TimeUnit::Nanosecond), Interval(IntervalUnit::MonthDayNano)) => {
2103            cast_duration_to_interval::<DurationNanosecondType>(array, cast_options)
2104        }
2105        (Interval(IntervalUnit::MonthDayNano), Duration(TimeUnit::Second)) => {
2106            cast_month_day_nano_to_duration::<DurationSecondType>(array, cast_options)
2107        }
2108        (Interval(IntervalUnit::MonthDayNano), Duration(TimeUnit::Millisecond)) => {
2109            cast_month_day_nano_to_duration::<DurationMillisecondType>(array, cast_options)
2110        }
2111        (Interval(IntervalUnit::MonthDayNano), Duration(TimeUnit::Microsecond)) => {
2112            cast_month_day_nano_to_duration::<DurationMicrosecondType>(array, cast_options)
2113        }
2114        (Interval(IntervalUnit::MonthDayNano), Duration(TimeUnit::Nanosecond)) => {
2115            cast_month_day_nano_to_duration::<DurationNanosecondType>(array, cast_options)
2116        }
2117        (Interval(IntervalUnit::YearMonth), Interval(IntervalUnit::MonthDayNano)) => {
2118            cast_interval_year_month_to_interval_month_day_nano(array, cast_options)
2119        }
2120        (Interval(IntervalUnit::DayTime), Interval(IntervalUnit::MonthDayNano)) => {
2121            cast_interval_day_time_to_interval_month_day_nano(array, cast_options)
2122        }
2123        (Int32, Interval(IntervalUnit::YearMonth)) => {
2124            cast_reinterpret_arrays::<Int32Type, IntervalYearMonthType>(array)
2125        }
2126        (_, _) => Err(ArrowError::CastError(format!(
2127            "Casting from {from_type} to {to_type} not supported",
2128        ))),
2129    }
2130}
2131
2132fn cast_from_decimal<D, F>(
2133    array: &dyn Array,
2134    scale: &i8,
2135    from_type: &DataType,
2136    to_type: &DataType,
2137    as_float: F,
2138    cast_options: &CastOptions,
2139) -> Result<ArrayRef, ArrowError>
2140where
2141    D: DecimalType + ArrowPrimitiveType,
2142    <D as ArrowPrimitiveType>::Native: ToPrimitive,
2143    F: Fn(D::Native) -> f64,
2144{
2145    use DataType::*;
2146    // cast decimal to other type
2147    match to_type {
2148        UInt8 => cast_decimal_to_integer::<D, UInt8Type>(array, *scale, cast_options),
2149        UInt16 => cast_decimal_to_integer::<D, UInt16Type>(array, *scale, cast_options),
2150        UInt32 => cast_decimal_to_integer::<D, UInt32Type>(array, *scale, cast_options),
2151        UInt64 => cast_decimal_to_integer::<D, UInt64Type>(array, *scale, cast_options),
2152        Int8 => cast_decimal_to_integer::<D, Int8Type>(array, *scale, cast_options),
2153        Int16 => cast_decimal_to_integer::<D, Int16Type>(array, *scale, cast_options),
2154        Int32 => cast_decimal_to_integer::<D, Int32Type>(array, *scale, cast_options),
2155        Int64 => cast_decimal_to_integer::<D, Int64Type>(array, *scale, cast_options),
2156        Float16 => cast_decimal_to_float::<D, Float16Type, _>(array, |x| {
2157            half::f16::from_f64(single_decimal_to_float_lossy::<D, F>(
2158                &as_float,
2159                x,
2160                <i32 as From<i8>>::from(*scale),
2161            ))
2162        }),
2163        Float32 => cast_decimal_to_f32::<D, F>(array, &as_float, *scale),
2164        Float64 => cast_decimal_to_f64::<D, F>(array, &as_float, *scale),
2165        Utf8View => value_to_string_view(array, cast_options),
2166        Utf8 => value_to_string::<i32>(array, cast_options),
2167        LargeUtf8 => value_to_string::<i64>(array, cast_options),
2168        Null => Ok(new_null_array(to_type, array.len())),
2169        _ => Err(ArrowError::CastError(format!(
2170            "Casting from {from_type} to {to_type} not supported"
2171        ))),
2172    }
2173}
2174
2175fn cast_to_decimal<D, M>(
2176    array: &dyn Array,
2177    precision: &u8,
2178    scale: &i8,
2179    from_type: &DataType,
2180    to_type: &DataType,
2181    cast_options: &CastOptions,
2182) -> Result<ArrayRef, ArrowError>
2183where
2184    D: DecimalType + ArrowPrimitiveType<Native = M>,
2185    M: ArrowNativeTypeOp + DecimalCast,
2186{
2187    use DataType::*;
2188    // cast data to decimal
2189    match from_type {
2190        UInt8 => cast_integer_to_decimal::<_, D, M>(
2191            array.as_primitive::<UInt8Type>(),
2192            *precision,
2193            *scale,
2194            cast_options,
2195        ),
2196        UInt16 => cast_integer_to_decimal::<_, D, _>(
2197            array.as_primitive::<UInt16Type>(),
2198            *precision,
2199            *scale,
2200            cast_options,
2201        ),
2202        UInt32 => cast_integer_to_decimal::<_, D, _>(
2203            array.as_primitive::<UInt32Type>(),
2204            *precision,
2205            *scale,
2206            cast_options,
2207        ),
2208        UInt64 => cast_integer_to_decimal::<_, D, _>(
2209            array.as_primitive::<UInt64Type>(),
2210            *precision,
2211            *scale,
2212            cast_options,
2213        ),
2214        Int8 => cast_integer_to_decimal::<_, D, _>(
2215            array.as_primitive::<Int8Type>(),
2216            *precision,
2217            *scale,
2218            cast_options,
2219        ),
2220        Int16 => cast_integer_to_decimal::<_, D, _>(
2221            array.as_primitive::<Int16Type>(),
2222            *precision,
2223            *scale,
2224            cast_options,
2225        ),
2226        Int32 => cast_integer_to_decimal::<_, D, _>(
2227            array.as_primitive::<Int32Type>(),
2228            *precision,
2229            *scale,
2230            cast_options,
2231        ),
2232        Int64 => cast_integer_to_decimal::<_, D, _>(
2233            array.as_primitive::<Int64Type>(),
2234            *precision,
2235            *scale,
2236            cast_options,
2237        ),
2238        Float16 => cast_floating_point_to_decimal::<_, D>(
2239            array.as_primitive::<Float16Type>(),
2240            *precision,
2241            *scale,
2242            cast_options,
2243        ),
2244        Float32 => cast_floating_point_to_decimal::<_, D>(
2245            array.as_primitive::<Float32Type>(),
2246            *precision,
2247            *scale,
2248            cast_options,
2249        ),
2250        Float64 => cast_floating_point_to_decimal::<_, D>(
2251            array.as_primitive::<Float64Type>(),
2252            *precision,
2253            *scale,
2254            cast_options,
2255        ),
2256        Utf8View | Utf8 => {
2257            cast_string_to_decimal::<D, i32>(array, *precision, *scale, cast_options)
2258        }
2259        LargeUtf8 => cast_string_to_decimal::<D, i64>(array, *precision, *scale, cast_options),
2260        Null => Ok(new_null_array(to_type, array.len())),
2261        _ => Err(ArrowError::CastError(format!(
2262            "Casting from {from_type} to {to_type} not supported"
2263        ))),
2264    }
2265}
2266
2267/// Number of `T` units in one day
2268const fn units_per_day<T: ArrowTimestampType>() -> i64 {
2269    SECONDS_IN_DAY * time_unit_multiple(&T::UNIT)
2270}
2271
2272/// Get the time unit as a multiple of a second
2273const fn time_unit_multiple(unit: &TimeUnit) -> i64 {
2274    match unit {
2275        TimeUnit::Second => 1,
2276        TimeUnit::Millisecond => MILLISECONDS,
2277        TimeUnit::Microsecond => MICROSECONDS,
2278        TimeUnit::Nanosecond => NANOSECONDS,
2279    }
2280}
2281
2282fn cast_time64_to_time32<FROM, TO>(
2283    array: &dyn Array,
2284    divisor: i64,
2285    cast_options: &CastOptions,
2286) -> Result<ArrayRef, ArrowError>
2287where
2288    FROM: ArrowPrimitiveType<Native = i64>,
2289    TO: ArrowPrimitiveType<Native = i32>,
2290{
2291    let array = array.as_primitive::<FROM>();
2292    let result = if cast_options.safe {
2293        array.unary_opt::<_, TO>(|value| i32::try_from(value / divisor).ok())
2294    } else {
2295        array.try_unary::<_, TO, _>(|value| {
2296            let value = value / divisor;
2297            i32::try_from(value).map_err(|_| {
2298                ArrowError::CastError(format!(
2299                    "Can't cast value {value:?} to type {}",
2300                    TO::DATA_TYPE
2301                ))
2302            })
2303        })?
2304    };
2305
2306    Ok(Arc::new(result))
2307}
2308
2309#[cfg(test)]
2310mod tests {
2311    use super::*;
2312    use crate::cast::numeric::{NumericNative, is_infallible_numeric_cast};
2313    use crate::parse::parse_decimal;
2314    use DataType::*;
2315    use arrow_array::{Int64Array, RunArray, StringArray};
2316    use arrow_buffer::{BooleanBuffer, IntervalDayTime, NullBuffer, i256};
2317    use arrow_schema::{DataType, Field};
2318    use chrono::{FixedOffset, NaiveDate, NaiveTime};
2319    use half::f16;
2320    use std::sync::Arc;
2321
2322    #[derive(Clone)]
2323    struct DecimalCastTestConfig {
2324        input_prec: u8,
2325        input_scale: i8,
2326        input_repr: i128,
2327        output_prec: u8,
2328        output_scale: i8,
2329        expected_output_repr: Result<i128, String>, // the error variant can contain a string
2330                                                    // template where the "{}" will be
2331                                                    // replaced with the decimal type name
2332                                                    // (e.g. Decimal128)
2333    }
2334
2335    macro_rules! generate_cast_test_case {
2336        ($INPUT_ARRAY: expr, $OUTPUT_TYPE_ARRAY: ident, $OUTPUT_TYPE: expr, $OUTPUT_VALUES: expr) => {
2337            let output =
2338                $OUTPUT_TYPE_ARRAY::from($OUTPUT_VALUES).with_data_type($OUTPUT_TYPE.clone());
2339
2340            // assert cast type
2341            let input_array_type = $INPUT_ARRAY.data_type();
2342            assert!(can_cast_types(input_array_type, $OUTPUT_TYPE));
2343            let result = cast($INPUT_ARRAY, $OUTPUT_TYPE).unwrap();
2344            assert_eq!($OUTPUT_TYPE, result.data_type());
2345            assert_eq!(result.as_ref(), &output);
2346
2347            let cast_option = CastOptions {
2348                safe: false,
2349                format_options: FormatOptions::default(),
2350            };
2351            let result = cast_with_options($INPUT_ARRAY, $OUTPUT_TYPE, &cast_option).unwrap();
2352            assert_eq!($OUTPUT_TYPE, result.data_type());
2353            assert_eq!(result.as_ref(), &output);
2354        };
2355    }
2356
2357    fn run_decimal_cast_test_case<I, O>(t: DecimalCastTestConfig)
2358    where
2359        I: DecimalType,
2360        O: DecimalType,
2361        I::Native: DecimalCast,
2362        O::Native: DecimalCast,
2363    {
2364        let array = vec![I::Native::from_decimal(t.input_repr)];
2365        let array = array
2366            .into_iter()
2367            .collect::<PrimitiveArray<I>>()
2368            .with_precision_and_scale(t.input_prec, t.input_scale)
2369            .unwrap();
2370        let input_type = array.data_type();
2371        let output_type = O::TYPE_CONSTRUCTOR(t.output_prec, t.output_scale);
2372        assert!(can_cast_types(input_type, &output_type));
2373
2374        let options = CastOptions {
2375            safe: false,
2376            ..Default::default()
2377        };
2378        let result = cast_with_options(&array, &output_type, &options);
2379
2380        match t.expected_output_repr {
2381            Ok(v) => {
2382                let expected_array = vec![O::Native::from_decimal(v)];
2383                let expected_array = expected_array
2384                    .into_iter()
2385                    .collect::<PrimitiveArray<O>>()
2386                    .with_precision_and_scale(t.output_prec, t.output_scale)
2387                    .unwrap();
2388                assert_eq!(*result.unwrap(), expected_array);
2389            }
2390            Err(expected_output_message_template) => {
2391                assert!(result.is_err());
2392                let expected_error_message =
2393                    expected_output_message_template.replace("{}", O::PREFIX);
2394                assert_eq!(result.unwrap_err().to_string(), expected_error_message);
2395            }
2396        }
2397    }
2398
2399    fn create_decimal32_array(
2400        array: Vec<Option<i32>>,
2401        precision: u8,
2402        scale: i8,
2403    ) -> Result<Decimal32Array, ArrowError> {
2404        array
2405            .into_iter()
2406            .collect::<Decimal32Array>()
2407            .with_precision_and_scale(precision, scale)
2408    }
2409
2410    fn create_decimal64_array(
2411        array: Vec<Option<i64>>,
2412        precision: u8,
2413        scale: i8,
2414    ) -> Result<Decimal64Array, ArrowError> {
2415        array
2416            .into_iter()
2417            .collect::<Decimal64Array>()
2418            .with_precision_and_scale(precision, scale)
2419    }
2420
2421    fn create_decimal128_array(
2422        array: Vec<Option<i128>>,
2423        precision: u8,
2424        scale: i8,
2425    ) -> Result<Decimal128Array, ArrowError> {
2426        array
2427            .into_iter()
2428            .collect::<Decimal128Array>()
2429            .with_precision_and_scale(precision, scale)
2430    }
2431
2432    fn create_decimal256_array(
2433        array: Vec<Option<i256>>,
2434        precision: u8,
2435        scale: i8,
2436    ) -> Result<Decimal256Array, ArrowError> {
2437        array
2438            .into_iter()
2439            .collect::<Decimal256Array>()
2440            .with_precision_and_scale(precision, scale)
2441    }
2442
2443    #[test]
2444    #[should_panic(
2445        expected = "Cannot cast to Decimal128(20, 3). Overflowing on 57896044618658097711785492504343953926634992332820282019728792003956564819967"
2446    )]
2447    fn test_cast_decimal_to_decimal_round_with_error() {
2448        // decimal256 to decimal128 overflow
2449        let array = vec![
2450            Some(i256::from_i128(1123454)),
2451            Some(i256::from_i128(2123456)),
2452            Some(i256::from_i128(-3123453)),
2453            Some(i256::from_i128(-3123456)),
2454            None,
2455            Some(i256::MAX),
2456            Some(i256::MIN),
2457        ];
2458        let input_decimal_array = create_decimal256_array(array, 76, 4).unwrap();
2459        let array = Arc::new(input_decimal_array) as ArrayRef;
2460        let input_type = DataType::Decimal256(76, 4);
2461        let output_type = DataType::Decimal128(20, 3);
2462        assert!(can_cast_types(&input_type, &output_type));
2463        generate_cast_test_case!(
2464            &array,
2465            Decimal128Array,
2466            &output_type,
2467            vec![
2468                Some(112345_i128),
2469                Some(212346_i128),
2470                Some(-312345_i128),
2471                Some(-312346_i128),
2472                None,
2473                None,
2474                None,
2475            ]
2476        );
2477    }
2478
2479    #[test]
2480    fn test_cast_decimal_to_decimal_round() {
2481        let array = vec![
2482            Some(1123454),
2483            Some(2123456),
2484            Some(-3123453),
2485            Some(-3123456),
2486            None,
2487        ];
2488        let array = create_decimal128_array(array, 20, 4).unwrap();
2489        // decimal128 to decimal128
2490        let input_type = DataType::Decimal128(20, 4);
2491        let output_type = DataType::Decimal128(20, 3);
2492        assert!(can_cast_types(&input_type, &output_type));
2493        generate_cast_test_case!(
2494            &array,
2495            Decimal128Array,
2496            &output_type,
2497            vec![
2498                Some(112345_i128),
2499                Some(212346_i128),
2500                Some(-312345_i128),
2501                Some(-312346_i128),
2502                None
2503            ]
2504        );
2505
2506        // decimal128 to decimal256
2507        let input_type = DataType::Decimal128(20, 4);
2508        let output_type = DataType::Decimal256(20, 3);
2509        assert!(can_cast_types(&input_type, &output_type));
2510        generate_cast_test_case!(
2511            &array,
2512            Decimal256Array,
2513            &output_type,
2514            vec![
2515                Some(i256::from_i128(112345_i128)),
2516                Some(i256::from_i128(212346_i128)),
2517                Some(i256::from_i128(-312345_i128)),
2518                Some(i256::from_i128(-312346_i128)),
2519                None
2520            ]
2521        );
2522
2523        // decimal256
2524        let array = vec![
2525            Some(i256::from_i128(1123454)),
2526            Some(i256::from_i128(2123456)),
2527            Some(i256::from_i128(-3123453)),
2528            Some(i256::from_i128(-3123456)),
2529            None,
2530        ];
2531        let array = create_decimal256_array(array, 20, 4).unwrap();
2532
2533        // decimal256 to decimal256
2534        let input_type = DataType::Decimal256(20, 4);
2535        let output_type = DataType::Decimal256(20, 3);
2536        assert!(can_cast_types(&input_type, &output_type));
2537        generate_cast_test_case!(
2538            &array,
2539            Decimal256Array,
2540            &output_type,
2541            vec![
2542                Some(i256::from_i128(112345_i128)),
2543                Some(i256::from_i128(212346_i128)),
2544                Some(i256::from_i128(-312345_i128)),
2545                Some(i256::from_i128(-312346_i128)),
2546                None
2547            ]
2548        );
2549        // decimal256 to decimal128
2550        let input_type = DataType::Decimal256(20, 4);
2551        let output_type = DataType::Decimal128(20, 3);
2552        assert!(can_cast_types(&input_type, &output_type));
2553        generate_cast_test_case!(
2554            &array,
2555            Decimal128Array,
2556            &output_type,
2557            vec![
2558                Some(112345_i128),
2559                Some(212346_i128),
2560                Some(-312345_i128),
2561                Some(-312346_i128),
2562                None
2563            ]
2564        );
2565    }
2566
2567    #[test]
2568    fn test_cast_decimal32_to_decimal32() {
2569        // test changing precision
2570        let input_type = DataType::Decimal32(9, 3);
2571        let output_type = DataType::Decimal32(9, 4);
2572        assert!(can_cast_types(&input_type, &output_type));
2573        let array = vec![Some(1123456), Some(2123456), Some(3123456), None];
2574        let array = create_decimal32_array(array, 9, 3).unwrap();
2575        generate_cast_test_case!(
2576            &array,
2577            Decimal32Array,
2578            &output_type,
2579            vec![
2580                Some(11234560_i32),
2581                Some(21234560_i32),
2582                Some(31234560_i32),
2583                None
2584            ]
2585        );
2586        // negative test
2587        let array = vec![Some(123456), None];
2588        let array = create_decimal32_array(array, 9, 0).unwrap();
2589        let result_safe = cast(&array, &DataType::Decimal32(2, 2));
2590        assert!(result_safe.is_ok());
2591        let options = CastOptions {
2592            safe: false,
2593            ..Default::default()
2594        };
2595
2596        let result_unsafe = cast_with_options(&array, &DataType::Decimal32(2, 2), &options);
2597        assert_eq!(
2598            "Invalid argument error: 123456.00 is too large to store in a Decimal32 of precision 2. Max is 0.99",
2599            result_unsafe.unwrap_err().to_string()
2600        );
2601    }
2602
2603    #[test]
2604    fn test_cast_decimal64_to_decimal64() {
2605        // test changing precision
2606        let input_type = DataType::Decimal64(17, 3);
2607        let output_type = DataType::Decimal64(17, 4);
2608        assert!(can_cast_types(&input_type, &output_type));
2609        let array = vec![Some(1123456), Some(2123456), Some(3123456), None];
2610        let array = create_decimal64_array(array, 17, 3).unwrap();
2611        generate_cast_test_case!(
2612            &array,
2613            Decimal64Array,
2614            &output_type,
2615            vec![
2616                Some(11234560_i64),
2617                Some(21234560_i64),
2618                Some(31234560_i64),
2619                None
2620            ]
2621        );
2622        // negative test
2623        let array = vec![Some(123456), None];
2624        let array = create_decimal64_array(array, 9, 0).unwrap();
2625        let result_safe = cast(&array, &DataType::Decimal64(2, 2));
2626        assert!(result_safe.is_ok());
2627        let options = CastOptions {
2628            safe: false,
2629            ..Default::default()
2630        };
2631
2632        let result_unsafe = cast_with_options(&array, &DataType::Decimal64(2, 2), &options);
2633        assert_eq!(
2634            "Invalid argument error: 123456.00 is too large to store in a Decimal64 of precision 2. Max is 0.99",
2635            result_unsafe.unwrap_err().to_string()
2636        );
2637    }
2638
2639    #[test]
2640    fn test_cast_decimal128_to_decimal128() {
2641        // test changing precision
2642        let input_type = DataType::Decimal128(20, 3);
2643        let output_type = DataType::Decimal128(20, 4);
2644        assert!(can_cast_types(&input_type, &output_type));
2645        let array = vec![Some(1123456), Some(2123456), Some(3123456), None];
2646        let array = create_decimal128_array(array, 20, 3).unwrap();
2647        generate_cast_test_case!(
2648            &array,
2649            Decimal128Array,
2650            &output_type,
2651            vec![
2652                Some(11234560_i128),
2653                Some(21234560_i128),
2654                Some(31234560_i128),
2655                None
2656            ]
2657        );
2658        // negative test
2659        let array = vec![Some(123456), None];
2660        let array = create_decimal128_array(array, 10, 0).unwrap();
2661        let result_safe = cast(&array, &DataType::Decimal128(2, 2));
2662        assert!(result_safe.is_ok());
2663        let options = CastOptions {
2664            safe: false,
2665            ..Default::default()
2666        };
2667
2668        let result_unsafe = cast_with_options(&array, &DataType::Decimal128(2, 2), &options);
2669        assert_eq!(
2670            "Invalid argument error: 123456.00 is too large to store in a Decimal128 of precision 2. Max is 0.99",
2671            result_unsafe.unwrap_err().to_string()
2672        );
2673    }
2674
2675    #[test]
2676    fn test_cast_decimal32_to_decimal32_dict() {
2677        let p = 9;
2678        let s = 3;
2679        let input_type = DataType::Decimal32(p, s);
2680        let output_type = DataType::Dictionary(
2681            Box::new(DataType::Int32),
2682            Box::new(DataType::Decimal32(p, s)),
2683        );
2684        assert!(can_cast_types(&input_type, &output_type));
2685        let array = vec![Some(1123456), Some(2123456), Some(3123456), None];
2686        let array = create_decimal32_array(array, p, s).unwrap();
2687        let cast_array = cast_with_options(&array, &output_type, &CastOptions::default()).unwrap();
2688        assert_eq!(cast_array.data_type(), &output_type);
2689    }
2690
2691    #[test]
2692    fn test_cast_decimal64_to_decimal64_dict() {
2693        let p = 15;
2694        let s = 3;
2695        let input_type = DataType::Decimal64(p, s);
2696        let output_type = DataType::Dictionary(
2697            Box::new(DataType::Int32),
2698            Box::new(DataType::Decimal64(p, s)),
2699        );
2700        assert!(can_cast_types(&input_type, &output_type));
2701        let array = vec![Some(1123456), Some(2123456), Some(3123456), None];
2702        let array = create_decimal64_array(array, p, s).unwrap();
2703        let cast_array = cast_with_options(&array, &output_type, &CastOptions::default()).unwrap();
2704        assert_eq!(cast_array.data_type(), &output_type);
2705    }
2706
2707    #[test]
2708    fn test_cast_decimal128_to_decimal128_dict() {
2709        let p = 20;
2710        let s = 3;
2711        let input_type = DataType::Decimal128(p, s);
2712        let output_type = DataType::Dictionary(
2713            Box::new(DataType::Int32),
2714            Box::new(DataType::Decimal128(p, s)),
2715        );
2716        assert!(can_cast_types(&input_type, &output_type));
2717        let array = vec![Some(1123456), Some(2123456), Some(3123456), None];
2718        let array = create_decimal128_array(array, p, s).unwrap();
2719        let cast_array = cast_with_options(&array, &output_type, &CastOptions::default()).unwrap();
2720        assert_eq!(cast_array.data_type(), &output_type);
2721    }
2722
2723    #[test]
2724    fn test_cast_decimal256_to_decimal256_dict() {
2725        let p = 20;
2726        let s = 3;
2727        let input_type = DataType::Decimal256(p, s);
2728        let output_type = DataType::Dictionary(
2729            Box::new(DataType::Int32),
2730            Box::new(DataType::Decimal256(p, s)),
2731        );
2732        assert!(can_cast_types(&input_type, &output_type));
2733        let array = vec![Some(1123456), Some(2123456), Some(3123456), None];
2734        let array = create_decimal128_array(array, p, s).unwrap();
2735        let cast_array = cast_with_options(&array, &output_type, &CastOptions::default()).unwrap();
2736        assert_eq!(cast_array.data_type(), &output_type);
2737    }
2738
2739    #[test]
2740    fn test_cast_decimal32_to_decimal32_overflow() {
2741        let input_type = DataType::Decimal32(9, 3);
2742        let output_type = DataType::Decimal32(9, 9);
2743        assert!(can_cast_types(&input_type, &output_type));
2744
2745        let array = vec![Some(i32::MAX)];
2746        let array = create_decimal32_array(array, 9, 3).unwrap();
2747        let result = cast_with_options(
2748            &array,
2749            &output_type,
2750            &CastOptions {
2751                safe: false,
2752                format_options: FormatOptions::default(),
2753            },
2754        );
2755        assert_eq!(
2756            "Cast error: Cannot cast to Decimal32(9, 9). Overflowing on 2147483647",
2757            result.unwrap_err().to_string()
2758        );
2759    }
2760
2761    #[test]
2762    fn test_cast_decimal32_to_decimal32_large_scale_reduction() {
2763        let array = vec![Some(-999999999), Some(0), Some(999999999), None];
2764        let array = create_decimal32_array(array, 9, 3).unwrap();
2765
2766        // Divide out all digits of precision -- rounding could still produce +/- 1
2767        let output_type = DataType::Decimal32(9, -6);
2768        assert!(can_cast_types(array.data_type(), &output_type));
2769        generate_cast_test_case!(
2770            &array,
2771            Decimal32Array,
2772            &output_type,
2773            vec![Some(-1), Some(0), Some(1), None]
2774        );
2775
2776        // Divide out more digits than we have precision -- all-zero result
2777        let output_type = DataType::Decimal32(9, -7);
2778        assert!(can_cast_types(array.data_type(), &output_type));
2779        generate_cast_test_case!(
2780            &array,
2781            Decimal32Array,
2782            &output_type,
2783            vec![Some(0), Some(0), Some(0), None]
2784        );
2785    }
2786
2787    #[test]
2788    fn test_cast_decimal64_to_decimal64_overflow() {
2789        let input_type = DataType::Decimal64(18, 3);
2790        let output_type = DataType::Decimal64(18, 18);
2791        assert!(can_cast_types(&input_type, &output_type));
2792
2793        let array = vec![Some(i64::MAX)];
2794        let array = create_decimal64_array(array, 18, 3).unwrap();
2795        let result = cast_with_options(
2796            &array,
2797            &output_type,
2798            &CastOptions {
2799                safe: false,
2800                format_options: FormatOptions::default(),
2801            },
2802        );
2803        assert_eq!(
2804            "Cast error: Cannot cast to Decimal64(18, 18). Overflowing on 9223372036854775807",
2805            result.unwrap_err().to_string()
2806        );
2807    }
2808
2809    #[test]
2810    fn test_cast_decimal64_to_decimal64_large_scale_reduction() {
2811        let array = vec![
2812            Some(-999999999999999999),
2813            Some(0),
2814            Some(999999999999999999),
2815            None,
2816        ];
2817        let array = create_decimal64_array(array, 18, 3).unwrap();
2818
2819        // Divide out all digits of precision -- rounding could still produce +/- 1
2820        let output_type = DataType::Decimal64(18, -15);
2821        assert!(can_cast_types(array.data_type(), &output_type));
2822        generate_cast_test_case!(
2823            &array,
2824            Decimal64Array,
2825            &output_type,
2826            vec![Some(-1), Some(0), Some(1), None]
2827        );
2828
2829        // Divide out more digits than we have precision -- all-zero result
2830        let output_type = DataType::Decimal64(18, -16);
2831        assert!(can_cast_types(array.data_type(), &output_type));
2832        generate_cast_test_case!(
2833            &array,
2834            Decimal64Array,
2835            &output_type,
2836            vec![Some(0), Some(0), Some(0), None]
2837        );
2838    }
2839
2840    #[test]
2841    fn test_cast_floating_to_decimals() {
2842        for output_type in [
2843            DataType::Decimal32(9, 3),
2844            DataType::Decimal64(9, 3),
2845            DataType::Decimal128(9, 3),
2846            DataType::Decimal256(9, 3),
2847        ] {
2848            let input_type = DataType::Float64;
2849            assert!(can_cast_types(&input_type, &output_type));
2850
2851            let array = vec![Some(1.1_f64)];
2852            let array = PrimitiveArray::<Float64Type>::from_iter(array);
2853            let result = cast_with_options(
2854                &array,
2855                &output_type,
2856                &CastOptions {
2857                    safe: false,
2858                    format_options: FormatOptions::default(),
2859                },
2860            );
2861            assert!(
2862                result.is_ok(),
2863                "Failed to cast to {output_type} with: {}",
2864                result.unwrap_err()
2865            );
2866        }
2867    }
2868
2869    #[test]
2870    #[cfg_attr(miri, ignore)] // Takes too long
2871    fn test_cast_float16_to_decimals() {
2872        let array = Float16Array::from(vec![
2873            Some(f16::from_f32(1.25)),
2874            Some(f16::from_f32(-2.5)),
2875            Some(f16::from_f32(1.125)),
2876            Some(f16::from_f32(-1.125)),
2877            Some(f16::from_f32(0.0)),
2878            None,
2879        ]);
2880
2881        generate_cast_test_case!(
2882            &array,
2883            Decimal32Array,
2884            &DataType::Decimal32(9, 2),
2885            vec![
2886                Some(125_i32),
2887                Some(-250_i32),
2888                Some(113_i32),
2889                Some(-113_i32),
2890                Some(0_i32),
2891                None
2892            ]
2893        );
2894        generate_cast_test_case!(
2895            &array,
2896            Decimal64Array,
2897            &DataType::Decimal64(18, 2),
2898            vec![
2899                Some(125_i64),
2900                Some(-250_i64),
2901                Some(113_i64),
2902                Some(-113_i64),
2903                Some(0_i64),
2904                None
2905            ]
2906        );
2907        generate_cast_test_case!(
2908            &array,
2909            Decimal128Array,
2910            &DataType::Decimal128(38, 2),
2911            vec![
2912                Some(125_i128),
2913                Some(-250_i128),
2914                Some(113_i128),
2915                Some(-113_i128),
2916                Some(0_i128),
2917                None
2918            ]
2919        );
2920        generate_cast_test_case!(
2921            &array,
2922            Decimal256Array,
2923            &DataType::Decimal256(76, 2),
2924            vec![
2925                Some(i256::from_i128(125_i128)),
2926                Some(i256::from_i128(-250_i128)),
2927                Some(i256::from_i128(113_i128)),
2928                Some(i256::from_i128(-113_i128)),
2929                Some(i256::from_i128(0_i128)),
2930                None
2931            ]
2932        );
2933
2934        let array = Float16Array::from(vec![
2935            Some(f16::from_f32(1250.0)),
2936            Some(f16::from_f32(-1250.0)),
2937            Some(f16::from_f32(1249.0)),
2938            None,
2939        ]);
2940        generate_cast_test_case!(
2941            &array,
2942            Decimal128Array,
2943            &DataType::Decimal128(5, -2),
2944            vec![Some(13_i128), Some(-13_i128), Some(12_i128), None]
2945        );
2946    }
2947
2948    #[test]
2949    fn test_cast_decimal128_to_decimal128_overflow() {
2950        let input_type = DataType::Decimal128(38, 3);
2951        let output_type = DataType::Decimal128(38, 38);
2952        assert!(can_cast_types(&input_type, &output_type));
2953
2954        let array = vec![Some(i128::MAX)];
2955        let array = create_decimal128_array(array, 38, 3).unwrap();
2956        let result = cast_with_options(
2957            &array,
2958            &output_type,
2959            &CastOptions {
2960                safe: false,
2961                format_options: FormatOptions::default(),
2962            },
2963        );
2964        assert_eq!(
2965            "Cast error: Cannot cast to Decimal128(38, 38). Overflowing on 170141183460469231731687303715884105727",
2966            result.unwrap_err().to_string()
2967        );
2968    }
2969
2970    #[test]
2971    fn test_cast_decimal128_to_decimal256_overflow() {
2972        let input_type = DataType::Decimal128(38, 3);
2973        let output_type = DataType::Decimal256(76, 76);
2974        assert!(can_cast_types(&input_type, &output_type));
2975
2976        let array = vec![Some(i128::MAX)];
2977        let array = create_decimal128_array(array, 38, 3).unwrap();
2978        let result = cast_with_options(
2979            &array,
2980            &output_type,
2981            &CastOptions {
2982                safe: false,
2983                format_options: FormatOptions::default(),
2984            },
2985        );
2986        assert_eq!(
2987            "Cast error: Cannot cast to Decimal256(76, 76). Overflowing on 170141183460469231731687303715884105727",
2988            result.unwrap_err().to_string()
2989        );
2990    }
2991
2992    #[test]
2993    fn test_cast_decimal32_to_decimal256() {
2994        let input_type = DataType::Decimal32(8, 3);
2995        let output_type = DataType::Decimal256(20, 4);
2996        assert!(can_cast_types(&input_type, &output_type));
2997        let array = vec![Some(1123456), Some(2123456), Some(3123456), None];
2998        let array = create_decimal32_array(array, 8, 3).unwrap();
2999        generate_cast_test_case!(
3000            &array,
3001            Decimal256Array,
3002            &output_type,
3003            vec![
3004                Some(i256::from_i128(11234560_i128)),
3005                Some(i256::from_i128(21234560_i128)),
3006                Some(i256::from_i128(31234560_i128)),
3007                None
3008            ]
3009        );
3010    }
3011    #[test]
3012    fn test_cast_decimal64_to_decimal256() {
3013        let input_type = DataType::Decimal64(12, 3);
3014        let output_type = DataType::Decimal256(20, 4);
3015        assert!(can_cast_types(&input_type, &output_type));
3016        let array = vec![Some(1123456), Some(2123456), Some(3123456), None];
3017        let array = create_decimal64_array(array, 12, 3).unwrap();
3018        generate_cast_test_case!(
3019            &array,
3020            Decimal256Array,
3021            &output_type,
3022            vec![
3023                Some(i256::from_i128(11234560_i128)),
3024                Some(i256::from_i128(21234560_i128)),
3025                Some(i256::from_i128(31234560_i128)),
3026                None
3027            ]
3028        );
3029    }
3030    #[test]
3031    fn test_cast_decimal128_to_decimal256() {
3032        let input_type = DataType::Decimal128(20, 3);
3033        let output_type = DataType::Decimal256(20, 4);
3034        assert!(can_cast_types(&input_type, &output_type));
3035        let array = vec![Some(1123456), Some(2123456), Some(3123456), None];
3036        let array = create_decimal128_array(array, 20, 3).unwrap();
3037        generate_cast_test_case!(
3038            &array,
3039            Decimal256Array,
3040            &output_type,
3041            vec![
3042                Some(i256::from_i128(11234560_i128)),
3043                Some(i256::from_i128(21234560_i128)),
3044                Some(i256::from_i128(31234560_i128)),
3045                None
3046            ]
3047        );
3048    }
3049
3050    #[test]
3051    fn test_cast_decimal256_to_decimal128_overflow() {
3052        let input_type = DataType::Decimal256(76, 5);
3053        let output_type = DataType::Decimal128(38, 7);
3054        assert!(can_cast_types(&input_type, &output_type));
3055        let array = vec![Some(i256::from_i128(i128::MAX))];
3056        let array = create_decimal256_array(array, 76, 5).unwrap();
3057        let result = cast_with_options(
3058            &array,
3059            &output_type,
3060            &CastOptions {
3061                safe: false,
3062                format_options: FormatOptions::default(),
3063            },
3064        );
3065        assert_eq!(
3066            "Cast error: Cannot cast to Decimal128(38, 7). Overflowing on 170141183460469231731687303715884105727",
3067            result.unwrap_err().to_string()
3068        );
3069    }
3070
3071    #[test]
3072    fn test_cast_decimal256_to_decimal256_overflow() {
3073        let input_type = DataType::Decimal256(76, 5);
3074        let output_type = DataType::Decimal256(76, 55);
3075        assert!(can_cast_types(&input_type, &output_type));
3076        let array = vec![Some(i256::from_i128(i128::MAX))];
3077        let array = create_decimal256_array(array, 76, 5).unwrap();
3078        let result = cast_with_options(
3079            &array,
3080            &output_type,
3081            &CastOptions {
3082                safe: false,
3083                format_options: FormatOptions::default(),
3084            },
3085        );
3086        assert_eq!(
3087            "Cast error: Cannot cast to Decimal256(76, 55). Overflowing on 170141183460469231731687303715884105727",
3088            result.unwrap_err().to_string()
3089        );
3090    }
3091
3092    #[test]
3093    fn test_cast_decimal256_to_decimal128() {
3094        let input_type = DataType::Decimal256(20, 3);
3095        let output_type = DataType::Decimal128(20, 4);
3096        assert!(can_cast_types(&input_type, &output_type));
3097        let array = vec![
3098            Some(i256::from_i128(1123456)),
3099            Some(i256::from_i128(2123456)),
3100            Some(i256::from_i128(3123456)),
3101            None,
3102        ];
3103        let array = create_decimal256_array(array, 20, 3).unwrap();
3104        generate_cast_test_case!(
3105            &array,
3106            Decimal128Array,
3107            &output_type,
3108            vec![
3109                Some(11234560_i128),
3110                Some(21234560_i128),
3111                Some(31234560_i128),
3112                None
3113            ]
3114        );
3115    }
3116
3117    #[test]
3118    fn test_cast_decimal256_to_decimal256() {
3119        let input_type = DataType::Decimal256(20, 3);
3120        let output_type = DataType::Decimal256(20, 4);
3121        assert!(can_cast_types(&input_type, &output_type));
3122        let array = vec![
3123            Some(i256::from_i128(1123456)),
3124            Some(i256::from_i128(2123456)),
3125            Some(i256::from_i128(3123456)),
3126            None,
3127        ];
3128        let array = create_decimal256_array(array, 20, 3).unwrap();
3129        generate_cast_test_case!(
3130            &array,
3131            Decimal256Array,
3132            &output_type,
3133            vec![
3134                Some(i256::from_i128(11234560_i128)),
3135                Some(i256::from_i128(21234560_i128)),
3136                Some(i256::from_i128(31234560_i128)),
3137                None
3138            ]
3139        );
3140    }
3141
3142    fn generate_decimal_to_numeric_cast_test_case<T>(array: &PrimitiveArray<T>)
3143    where
3144        T: ArrowPrimitiveType + DecimalType,
3145    {
3146        // u8
3147        generate_cast_test_case!(
3148            array,
3149            UInt8Array,
3150            &DataType::UInt8,
3151            vec![Some(1_u8), Some(2_u8), Some(3_u8), None, Some(5_u8)]
3152        );
3153        // u16
3154        generate_cast_test_case!(
3155            array,
3156            UInt16Array,
3157            &DataType::UInt16,
3158            vec![Some(1_u16), Some(2_u16), Some(3_u16), None, Some(5_u16)]
3159        );
3160        // u32
3161        generate_cast_test_case!(
3162            array,
3163            UInt32Array,
3164            &DataType::UInt32,
3165            vec![Some(1_u32), Some(2_u32), Some(3_u32), None, Some(5_u32)]
3166        );
3167        // u64
3168        generate_cast_test_case!(
3169            array,
3170            UInt64Array,
3171            &DataType::UInt64,
3172            vec![Some(1_u64), Some(2_u64), Some(3_u64), None, Some(5_u64)]
3173        );
3174        // i8
3175        generate_cast_test_case!(
3176            array,
3177            Int8Array,
3178            &DataType::Int8,
3179            vec![Some(1_i8), Some(2_i8), Some(3_i8), None, Some(5_i8)]
3180        );
3181        // i16
3182        generate_cast_test_case!(
3183            array,
3184            Int16Array,
3185            &DataType::Int16,
3186            vec![Some(1_i16), Some(2_i16), Some(3_i16), None, Some(5_i16)]
3187        );
3188        // i32
3189        generate_cast_test_case!(
3190            array,
3191            Int32Array,
3192            &DataType::Int32,
3193            vec![Some(1_i32), Some(2_i32), Some(3_i32), None, Some(5_i32)]
3194        );
3195        // i64
3196        generate_cast_test_case!(
3197            array,
3198            Int64Array,
3199            &DataType::Int64,
3200            vec![Some(1_i64), Some(2_i64), Some(3_i64), None, Some(5_i64)]
3201        );
3202        // f16
3203        generate_cast_test_case!(
3204            array,
3205            Float16Array,
3206            &DataType::Float16,
3207            vec![
3208                Some(f16::from_f32(1.25)),
3209                Some(f16::from_f32(2.25)),
3210                Some(f16::from_f32(3.25)),
3211                None,
3212                Some(f16::from_f32(5.25))
3213            ]
3214        );
3215        // f32
3216        generate_cast_test_case!(
3217            array,
3218            Float32Array,
3219            &DataType::Float32,
3220            vec![
3221                Some(1.25_f32),
3222                Some(2.25_f32),
3223                Some(3.25_f32),
3224                None,
3225                Some(5.25_f32)
3226            ]
3227        );
3228        // f64
3229        generate_cast_test_case!(
3230            array,
3231            Float64Array,
3232            &DataType::Float64,
3233            vec![
3234                Some(1.25_f64),
3235                Some(2.25_f64),
3236                Some(3.25_f64),
3237                None,
3238                Some(5.25_f64)
3239            ]
3240        );
3241    }
3242
3243    #[test]
3244    #[cfg_attr(miri, ignore)] // Takes too long
3245    fn test_cast_decimal32_to_numeric() {
3246        let value_array: Vec<Option<i32>> = vec![Some(125), Some(225), Some(325), None, Some(525)];
3247        let array = create_decimal32_array(value_array, 8, 2).unwrap();
3248
3249        generate_decimal_to_numeric_cast_test_case(&array);
3250    }
3251
3252    #[test]
3253    #[cfg_attr(miri, ignore)] // Takes too long
3254    fn test_cast_decimal64_to_numeric() {
3255        let value_array: Vec<Option<i64>> = vec![Some(125), Some(225), Some(325), None, Some(525)];
3256        let array = create_decimal64_array(value_array, 8, 2).unwrap();
3257
3258        generate_decimal_to_numeric_cast_test_case(&array);
3259    }
3260
3261    #[test]
3262    #[cfg_attr(miri, ignore)] // Takes too long
3263    fn test_cast_decimal128_to_numeric() {
3264        let value_array: Vec<Option<i128>> = vec![Some(125), Some(225), Some(325), None, Some(525)];
3265        let array = create_decimal128_array(value_array, 38, 2).unwrap();
3266
3267        generate_decimal_to_numeric_cast_test_case(&array);
3268
3269        // overflow test: out of range of max u8
3270        let value_array: Vec<Option<i128>> = vec![Some(51300)];
3271        let array = create_decimal128_array(value_array, 38, 2).unwrap();
3272        let casted_array = cast_with_options(
3273            &array,
3274            &DataType::UInt8,
3275            &CastOptions {
3276                safe: false,
3277                format_options: FormatOptions::default(),
3278            },
3279        );
3280        assert_eq!(
3281            "Cast error: value of 513 is out of range UInt8".to_string(),
3282            casted_array.unwrap_err().to_string()
3283        );
3284
3285        let casted_array = cast_with_options(
3286            &array,
3287            &DataType::UInt8,
3288            &CastOptions {
3289                safe: true,
3290                format_options: FormatOptions::default(),
3291            },
3292        );
3293        assert!(casted_array.is_ok());
3294        assert!(casted_array.unwrap().is_null(0));
3295
3296        // overflow test: out of range of max i8
3297        let value_array: Vec<Option<i128>> = vec![Some(24400)];
3298        let array = create_decimal128_array(value_array, 38, 2).unwrap();
3299        let casted_array = cast_with_options(
3300            &array,
3301            &DataType::Int8,
3302            &CastOptions {
3303                safe: false,
3304                format_options: FormatOptions::default(),
3305            },
3306        );
3307        assert_eq!(
3308            "Cast error: value of 244 is out of range Int8".to_string(),
3309            casted_array.unwrap_err().to_string()
3310        );
3311
3312        let casted_array = cast_with_options(
3313            &array,
3314            &DataType::Int8,
3315            &CastOptions {
3316                safe: true,
3317                format_options: FormatOptions::default(),
3318            },
3319        );
3320        assert!(casted_array.is_ok());
3321        assert!(casted_array.unwrap().is_null(0));
3322
3323        // loss the precision: convert decimal to f32、f64
3324        // f32
3325        // 112345678_f32 and 112345679_f32 are same, so the 112345679_f32 will lose precision.
3326        let value_array: Vec<Option<i128>> = vec![
3327            Some(125),
3328            Some(225),
3329            Some(325),
3330            None,
3331            Some(525),
3332            Some(112345678),
3333            Some(112345679),
3334        ];
3335        let array = create_decimal128_array(value_array, 38, 2).unwrap();
3336        generate_cast_test_case!(
3337            &array,
3338            Float32Array,
3339            &DataType::Float32,
3340            vec![
3341                Some(1.25_f32),
3342                Some(2.25_f32),
3343                Some(3.25_f32),
3344                None,
3345                Some(5.25_f32),
3346                Some(1_123_456.7_f32),
3347                Some(1_123_456.7_f32)
3348            ]
3349        );
3350
3351        // f64
3352        // 112345678901234568_f64 and 112345678901234560_f64 are same, so the 112345678901234568_f64 will lose precision.
3353        let value_array: Vec<Option<i128>> = vec![
3354            Some(125),
3355            Some(225),
3356            Some(325),
3357            None,
3358            Some(525),
3359            Some(112345678901234568),
3360            Some(112345678901234560),
3361        ];
3362        let array = create_decimal128_array(value_array, 38, 2).unwrap();
3363        generate_cast_test_case!(
3364            &array,
3365            Float64Array,
3366            &DataType::Float64,
3367            vec![
3368                Some(1.25_f64),
3369                Some(2.25_f64),
3370                Some(3.25_f64),
3371                None,
3372                Some(5.25_f64),
3373                Some(1_123_456_789_012_345.6_f64),
3374                Some(1_123_456_789_012_345.6_f64),
3375            ]
3376        );
3377    }
3378
3379    #[test]
3380    #[cfg_attr(miri, ignore)] // Takes too long
3381    fn test_cast_decimal256_to_numeric() {
3382        let value_array: Vec<Option<i256>> = vec![
3383            Some(i256::from_i128(125)),
3384            Some(i256::from_i128(225)),
3385            Some(i256::from_i128(325)),
3386            None,
3387            Some(i256::from_i128(525)),
3388        ];
3389        let array = create_decimal256_array(value_array, 38, 2).unwrap();
3390        // u8
3391        generate_cast_test_case!(
3392            &array,
3393            UInt8Array,
3394            &DataType::UInt8,
3395            vec![Some(1_u8), Some(2_u8), Some(3_u8), None, Some(5_u8)]
3396        );
3397        // u16
3398        generate_cast_test_case!(
3399            &array,
3400            UInt16Array,
3401            &DataType::UInt16,
3402            vec![Some(1_u16), Some(2_u16), Some(3_u16), None, Some(5_u16)]
3403        );
3404        // u32
3405        generate_cast_test_case!(
3406            &array,
3407            UInt32Array,
3408            &DataType::UInt32,
3409            vec![Some(1_u32), Some(2_u32), Some(3_u32), None, Some(5_u32)]
3410        );
3411        // u64
3412        generate_cast_test_case!(
3413            &array,
3414            UInt64Array,
3415            &DataType::UInt64,
3416            vec![Some(1_u64), Some(2_u64), Some(3_u64), None, Some(5_u64)]
3417        );
3418        // i8
3419        generate_cast_test_case!(
3420            &array,
3421            Int8Array,
3422            &DataType::Int8,
3423            vec![Some(1_i8), Some(2_i8), Some(3_i8), None, Some(5_i8)]
3424        );
3425        // i16
3426        generate_cast_test_case!(
3427            &array,
3428            Int16Array,
3429            &DataType::Int16,
3430            vec![Some(1_i16), Some(2_i16), Some(3_i16), None, Some(5_i16)]
3431        );
3432        // i32
3433        generate_cast_test_case!(
3434            &array,
3435            Int32Array,
3436            &DataType::Int32,
3437            vec![Some(1_i32), Some(2_i32), Some(3_i32), None, Some(5_i32)]
3438        );
3439        // i64
3440        generate_cast_test_case!(
3441            &array,
3442            Int64Array,
3443            &DataType::Int64,
3444            vec![Some(1_i64), Some(2_i64), Some(3_i64), None, Some(5_i64)]
3445        );
3446        // f16
3447        generate_cast_test_case!(
3448            &array,
3449            Float16Array,
3450            &DataType::Float16,
3451            vec![
3452                Some(f16::from_f32(1.25)),
3453                Some(f16::from_f32(2.25)),
3454                Some(f16::from_f32(3.25)),
3455                None,
3456                Some(f16::from_f32(5.25))
3457            ]
3458        );
3459        // f32
3460        generate_cast_test_case!(
3461            &array,
3462            Float32Array,
3463            &DataType::Float32,
3464            vec![
3465                Some(1.25_f32),
3466                Some(2.25_f32),
3467                Some(3.25_f32),
3468                None,
3469                Some(5.25_f32)
3470            ]
3471        );
3472        // f64
3473        generate_cast_test_case!(
3474            &array,
3475            Float64Array,
3476            &DataType::Float64,
3477            vec![
3478                Some(1.25_f64),
3479                Some(2.25_f64),
3480                Some(3.25_f64),
3481                None,
3482                Some(5.25_f64)
3483            ]
3484        );
3485
3486        // overflow test: out of range of max i8
3487        let value_array: Vec<Option<i256>> = vec![Some(i256::from_i128(24400))];
3488        let array = create_decimal256_array(value_array, 38, 2).unwrap();
3489        let casted_array = cast_with_options(
3490            &array,
3491            &DataType::Int8,
3492            &CastOptions {
3493                safe: false,
3494                format_options: FormatOptions::default(),
3495            },
3496        );
3497        assert_eq!(
3498            "Cast error: value of 244 is out of range Int8".to_string(),
3499            casted_array.unwrap_err().to_string()
3500        );
3501
3502        let casted_array = cast_with_options(
3503            &array,
3504            &DataType::Int8,
3505            &CastOptions {
3506                safe: true,
3507                format_options: FormatOptions::default(),
3508            },
3509        );
3510        assert!(casted_array.is_ok());
3511        assert!(casted_array.unwrap().is_null(0));
3512
3513        // overflow test: values whose low 64 bits fit the target type
3514        // https://github.com/apache/arrow-rs/issues/10855
3515        let value_array: Vec<Option<i256>> = vec![Some(i256::from_i128((1i128 << 64) + 5))];
3516        let array = create_decimal256_array(value_array, 76, 0).unwrap();
3517        let casted_array = cast_with_options(
3518            &array,
3519            &DataType::Int64,
3520            &CastOptions {
3521                safe: false,
3522                format_options: FormatOptions::default(),
3523            },
3524        );
3525        assert_eq!(
3526            "Cast error: value of 18446744073709551621 is out of range Int64".to_string(),
3527            casted_array.unwrap_err().to_string()
3528        );
3529
3530        let casted_array = cast_with_options(
3531            &array,
3532            &DataType::Int64,
3533            &CastOptions {
3534                safe: true,
3535                format_options: FormatOptions::default(),
3536            },
3537        );
3538        assert!(casted_array.is_ok());
3539        assert!(casted_array.unwrap().is_null(0));
3540
3541        // loss the precision: convert decimal to f32、f64
3542        // f32
3543        // 112345678_f32 and 112345679_f32 are same, so the 112345679_f32 will lose precision.
3544        let value_array: Vec<Option<i256>> = vec![
3545            Some(i256::from_i128(125)),
3546            Some(i256::from_i128(225)),
3547            Some(i256::from_i128(325)),
3548            None,
3549            Some(i256::from_i128(525)),
3550            Some(i256::from_i128(112345678)),
3551            Some(i256::from_i128(112345679)),
3552        ];
3553        let array = create_decimal256_array(value_array, 76, 2).unwrap();
3554        generate_cast_test_case!(
3555            &array,
3556            Float32Array,
3557            &DataType::Float32,
3558            vec![
3559                Some(1.25_f32),
3560                Some(2.25_f32),
3561                Some(3.25_f32),
3562                None,
3563                Some(5.25_f32),
3564                Some(1_123_456.7_f32),
3565                Some(1_123_456.7_f32)
3566            ]
3567        );
3568
3569        // f64
3570        // 112345678901234568_f64 and 112345678901234560_f64 are same, so the 112345678901234568_f64 will lose precision.
3571        let value_array: Vec<Option<i256>> = vec![
3572            Some(i256::from_i128(125)),
3573            Some(i256::from_i128(225)),
3574            Some(i256::from_i128(325)),
3575            None,
3576            Some(i256::from_i128(525)),
3577            Some(i256::from_i128(112345678901234568)),
3578            Some(i256::from_i128(112345678901234560)),
3579        ];
3580        let array = create_decimal256_array(value_array, 76, 2).unwrap();
3581        generate_cast_test_case!(
3582            &array,
3583            Float64Array,
3584            &DataType::Float64,
3585            vec![
3586                Some(1.25_f64),
3587                Some(2.25_f64),
3588                Some(3.25_f64),
3589                None,
3590                Some(5.25_f64),
3591                Some(1_123_456_789_012_345.6_f64),
3592                Some(1_123_456_789_012_345.6_f64),
3593            ]
3594        );
3595    }
3596
3597    #[test]
3598    #[cfg_attr(miri, ignore)] // Unsupported inline assembly
3599    fn test_cast_decimal128_to_float16_overflow() {
3600        let array = create_decimal128_array(
3601            vec![
3602                Some(6_550_400_i128),
3603                Some(100_000_000_i128),
3604                Some(-100_000_000_i128),
3605                None,
3606            ],
3607            10,
3608            2,
3609        )
3610        .unwrap();
3611
3612        generate_cast_test_case!(
3613            &array,
3614            Float16Array,
3615            &DataType::Float16,
3616            vec![
3617                Some(f16::from_f64(65504.0)),
3618                Some(f16::INFINITY),
3619                Some(f16::NEG_INFINITY),
3620                None
3621            ]
3622        );
3623    }
3624
3625    #[test]
3626    #[cfg_attr(miri, ignore)] // Unsupported inline assembly
3627    fn test_cast_decimal256_to_float16_overflow() {
3628        let array = create_decimal256_array(
3629            vec![
3630                Some(i256::from_i128(6_550_400_i128)),
3631                Some(i256::from_i128(100_000_000_i128)),
3632                Some(i256::from_i128(-100_000_000_i128)),
3633                None,
3634            ],
3635            10,
3636            2,
3637        )
3638        .unwrap();
3639
3640        generate_cast_test_case!(
3641            &array,
3642            Float16Array,
3643            &DataType::Float16,
3644            vec![
3645                Some(f16::from_f64(65504.0)),
3646                Some(f16::INFINITY),
3647                Some(f16::NEG_INFINITY),
3648                None
3649            ]
3650        );
3651    }
3652
3653    #[test]
3654    #[cfg_attr(miri, ignore)] // Unsupported inline assembly
3655    fn test_cast_decimal_to_numeric_negative_scale() {
3656        let value_array: Vec<Option<i256>> = vec![
3657            Some(i256::from_i128(125)),
3658            Some(i256::from_i128(225)),
3659            Some(i256::from_i128(325)),
3660            None,
3661            Some(i256::from_i128(525)),
3662        ];
3663        let array = create_decimal256_array(value_array, 38, -1).unwrap();
3664
3665        generate_cast_test_case!(
3666            &array,
3667            Int64Array,
3668            &DataType::Int64,
3669            vec![Some(1_250), Some(2_250), Some(3_250), None, Some(5_250)]
3670        );
3671
3672        let value_array: Vec<Option<i128>> = vec![Some(12), Some(-12), None];
3673        let array = create_decimal128_array(value_array, 10, -2).unwrap();
3674        generate_cast_test_case!(
3675            &array,
3676            Float16Array,
3677            &DataType::Float16,
3678            vec![
3679                Some(f16::from_f32(1200.0)),
3680                Some(f16::from_f32(-1200.0)),
3681                None
3682            ]
3683        );
3684
3685        let value_array: Vec<Option<i32>> = vec![Some(125), Some(225), Some(325), None, Some(525)];
3686        let array = create_decimal32_array(value_array, 8, -2).unwrap();
3687        generate_cast_test_case!(
3688            &array,
3689            Int64Array,
3690            &DataType::Int64,
3691            vec![Some(12_500), Some(22_500), Some(32_500), None, Some(52_500)]
3692        );
3693
3694        let value_array: Vec<Option<i32>> = vec![Some(2), Some(1), None];
3695        let array = create_decimal32_array(value_array, 9, -9).unwrap();
3696        generate_cast_test_case!(
3697            &array,
3698            Int64Array,
3699            &DataType::Int64,
3700            vec![Some(2_000_000_000), Some(1_000_000_000), None]
3701        );
3702
3703        let value_array: Vec<Option<i64>> = vec![Some(125), Some(225), Some(325), None, Some(525)];
3704        let array = create_decimal64_array(value_array, 18, -3).unwrap();
3705        generate_cast_test_case!(
3706            &array,
3707            Int64Array,
3708            &DataType::Int64,
3709            vec![
3710                Some(125_000),
3711                Some(225_000),
3712                Some(325_000),
3713                None,
3714                Some(525_000)
3715            ]
3716        );
3717
3718        let value_array: Vec<Option<i64>> = vec![Some(12), Some(34), None];
3719        let array = create_decimal64_array(value_array, 18, -10).unwrap();
3720        generate_cast_test_case!(
3721            &array,
3722            Int64Array,
3723            &DataType::Int64,
3724            vec![Some(120_000_000_000), Some(340_000_000_000), None]
3725        );
3726
3727        let value_array: Vec<Option<i128>> = vec![Some(125), Some(225), Some(325), None, Some(525)];
3728        let array = create_decimal128_array(value_array, 38, -4).unwrap();
3729        generate_cast_test_case!(
3730            &array,
3731            Int64Array,
3732            &DataType::Int64,
3733            vec![
3734                Some(1_250_000),
3735                Some(2_250_000),
3736                Some(3_250_000),
3737                None,
3738                Some(5_250_000)
3739            ]
3740        );
3741
3742        let value_array: Vec<Option<i128>> = vec![Some(9), Some(1), None];
3743        let array = create_decimal128_array(value_array, 38, -18).unwrap();
3744        generate_cast_test_case!(
3745            &array,
3746            Int64Array,
3747            &DataType::Int64,
3748            vec![
3749                Some(9_000_000_000_000_000_000),
3750                Some(1_000_000_000_000_000_000),
3751                None
3752            ]
3753        );
3754
3755        let array = create_decimal32_array(vec![Some(999_999_999)], 9, -1).unwrap();
3756        let casted_array = cast_with_options(
3757            &array,
3758            &DataType::Int64,
3759            &CastOptions {
3760                safe: false,
3761                format_options: FormatOptions::default(),
3762            },
3763        );
3764        assert_eq!(
3765            "Arithmetic overflow: Overflow happened on: 999999999 * 10".to_string(),
3766            casted_array.unwrap_err().to_string()
3767        );
3768
3769        let casted_array = cast_with_options(
3770            &array,
3771            &DataType::Int64,
3772            &CastOptions {
3773                safe: true,
3774                format_options: FormatOptions::default(),
3775            },
3776        );
3777        assert!(casted_array.is_ok());
3778        assert!(casted_array.unwrap().is_null(0));
3779
3780        let array = create_decimal64_array(vec![Some(13)], 18, -1).unwrap();
3781        let casted_array = cast_with_options(
3782            &array,
3783            &DataType::Int8,
3784            &CastOptions {
3785                safe: false,
3786                format_options: FormatOptions::default(),
3787            },
3788        );
3789        assert_eq!(
3790            "Cast error: value of 130 is out of range Int8".to_string(),
3791            casted_array.unwrap_err().to_string()
3792        );
3793
3794        let casted_array = cast_with_options(
3795            &array,
3796            &DataType::Int8,
3797            &CastOptions {
3798                safe: true,
3799                format_options: FormatOptions::default(),
3800            },
3801        );
3802        assert!(casted_array.is_ok());
3803        assert!(casted_array.unwrap().is_null(0));
3804    }
3805
3806    #[test]
3807    fn test_cast_numeric_to_decimal128() {
3808        let decimal_type = DataType::Decimal128(38, 6);
3809        // u8, u16, u32, u64
3810        let input_arrays = vec![
3811            Arc::new(UInt8Array::from(vec![
3812                Some(1),
3813                Some(2),
3814                Some(3),
3815                None,
3816                Some(5),
3817            ])) as ArrayRef, // u8
3818            Arc::new(UInt16Array::from(vec![
3819                Some(1),
3820                Some(2),
3821                Some(3),
3822                None,
3823                Some(5),
3824            ])) as ArrayRef, // u16
3825            Arc::new(UInt32Array::from(vec![
3826                Some(1),
3827                Some(2),
3828                Some(3),
3829                None,
3830                Some(5),
3831            ])) as ArrayRef, // u32
3832            Arc::new(UInt64Array::from(vec![
3833                Some(1),
3834                Some(2),
3835                Some(3),
3836                None,
3837                Some(5),
3838            ])) as ArrayRef, // u64
3839        ];
3840
3841        for array in input_arrays {
3842            generate_cast_test_case!(
3843                &array,
3844                Decimal128Array,
3845                &decimal_type,
3846                vec![
3847                    Some(1000000_i128),
3848                    Some(2000000_i128),
3849                    Some(3000000_i128),
3850                    None,
3851                    Some(5000000_i128)
3852                ]
3853            );
3854        }
3855
3856        // i8, i16, i32, i64
3857        let input_arrays = vec![
3858            Arc::new(Int8Array::from(vec![
3859                Some(1),
3860                Some(2),
3861                Some(3),
3862                None,
3863                Some(5),
3864            ])) as ArrayRef, // i8
3865            Arc::new(Int16Array::from(vec![
3866                Some(1),
3867                Some(2),
3868                Some(3),
3869                None,
3870                Some(5),
3871            ])) as ArrayRef, // i16
3872            Arc::new(Int32Array::from(vec![
3873                Some(1),
3874                Some(2),
3875                Some(3),
3876                None,
3877                Some(5),
3878            ])) as ArrayRef, // i32
3879            Arc::new(Int64Array::from(vec![
3880                Some(1),
3881                Some(2),
3882                Some(3),
3883                None,
3884                Some(5),
3885            ])) as ArrayRef, // i64
3886        ];
3887        for array in input_arrays {
3888            generate_cast_test_case!(
3889                &array,
3890                Decimal128Array,
3891                &decimal_type,
3892                vec![
3893                    Some(1000000_i128),
3894                    Some(2000000_i128),
3895                    Some(3000000_i128),
3896                    None,
3897                    Some(5000000_i128)
3898                ]
3899            );
3900        }
3901
3902        // test u8 to decimal type with overflow the result type
3903        // the 100 will be converted to 1000_i128, but it is out of range for max value in the precision 3.
3904        let array = UInt8Array::from(vec![1, 2, 3, 4, 100]);
3905        let casted_array = cast(&array, &DataType::Decimal128(3, 1));
3906        assert!(casted_array.is_ok());
3907        let array = casted_array.unwrap();
3908        let array: &Decimal128Array = array.as_primitive();
3909        assert!(array.is_null(4));
3910
3911        // test i8 to decimal type with overflow the result type
3912        // the 100 will be converted to 1000_i128, but it is out of range for max value in the precision 3.
3913        let array = Int8Array::from(vec![1, 2, 3, 4, 100]);
3914        let casted_array = cast(&array, &DataType::Decimal128(3, 1));
3915        assert!(casted_array.is_ok());
3916        let array = casted_array.unwrap();
3917        let array: &Decimal128Array = array.as_primitive();
3918        assert!(array.is_null(4));
3919
3920        // test f32 to decimal type
3921        let array = Float32Array::from(vec![
3922            Some(1.1),
3923            Some(2.2),
3924            Some(4.4),
3925            None,
3926            Some(1.123_456_4), // round down
3927            Some(1.123_456_7), // round up
3928        ]);
3929        let array = Arc::new(array) as ArrayRef;
3930        generate_cast_test_case!(
3931            &array,
3932            Decimal128Array,
3933            &decimal_type,
3934            vec![
3935                Some(1100000_i128),
3936                Some(2200000_i128),
3937                Some(4400000_i128),
3938                None,
3939                Some(1123456_i128), // round down
3940                Some(1123457_i128), // round up
3941            ]
3942        );
3943
3944        // test f64 to decimal type
3945        let array = Float64Array::from(vec![
3946            Some(1.1),
3947            Some(2.2),
3948            Some(4.4),
3949            None,
3950            Some(1.123_456_489_123_4),     // round up
3951            Some(1.123_456_789_123_4),     // round up
3952            Some(1.123_456_489_012_345_6), // round down
3953            Some(1.123_456_789_012_345_6), // round up
3954        ]);
3955        generate_cast_test_case!(
3956            &array,
3957            Decimal128Array,
3958            &decimal_type,
3959            vec![
3960                Some(1100000_i128),
3961                Some(2200000_i128),
3962                Some(4400000_i128),
3963                None,
3964                Some(1123456_i128), // round down
3965                Some(1123457_i128), // round up
3966                Some(1123456_i128), // round down
3967                Some(1123457_i128), // round up
3968            ]
3969        );
3970    }
3971
3972    #[test]
3973    fn test_cast_numeric_to_decimal256() {
3974        let decimal_type = DataType::Decimal256(76, 6);
3975        // u8, u16, u32, u64
3976        let input_arrays = vec![
3977            Arc::new(UInt8Array::from(vec![
3978                Some(1),
3979                Some(2),
3980                Some(3),
3981                None,
3982                Some(5),
3983            ])) as ArrayRef, // u8
3984            Arc::new(UInt16Array::from(vec![
3985                Some(1),
3986                Some(2),
3987                Some(3),
3988                None,
3989                Some(5),
3990            ])) as ArrayRef, // u16
3991            Arc::new(UInt32Array::from(vec![
3992                Some(1),
3993                Some(2),
3994                Some(3),
3995                None,
3996                Some(5),
3997            ])) as ArrayRef, // u32
3998            Arc::new(UInt64Array::from(vec![
3999                Some(1),
4000                Some(2),
4001                Some(3),
4002                None,
4003                Some(5),
4004            ])) as ArrayRef, // u64
4005        ];
4006
4007        for array in input_arrays {
4008            generate_cast_test_case!(
4009                &array,
4010                Decimal256Array,
4011                &decimal_type,
4012                vec![
4013                    Some(i256::from_i128(1000000_i128)),
4014                    Some(i256::from_i128(2000000_i128)),
4015                    Some(i256::from_i128(3000000_i128)),
4016                    None,
4017                    Some(i256::from_i128(5000000_i128))
4018                ]
4019            );
4020        }
4021
4022        // i8, i16, i32, i64
4023        let input_arrays = vec![
4024            Arc::new(Int8Array::from(vec![
4025                Some(1),
4026                Some(2),
4027                Some(3),
4028                None,
4029                Some(5),
4030            ])) as ArrayRef, // i8
4031            Arc::new(Int16Array::from(vec![
4032                Some(1),
4033                Some(2),
4034                Some(3),
4035                None,
4036                Some(5),
4037            ])) as ArrayRef, // i16
4038            Arc::new(Int32Array::from(vec![
4039                Some(1),
4040                Some(2),
4041                Some(3),
4042                None,
4043                Some(5),
4044            ])) as ArrayRef, // i32
4045            Arc::new(Int64Array::from(vec![
4046                Some(1),
4047                Some(2),
4048                Some(3),
4049                None,
4050                Some(5),
4051            ])) as ArrayRef, // i64
4052        ];
4053        for array in input_arrays {
4054            generate_cast_test_case!(
4055                &array,
4056                Decimal256Array,
4057                &decimal_type,
4058                vec![
4059                    Some(i256::from_i128(1000000_i128)),
4060                    Some(i256::from_i128(2000000_i128)),
4061                    Some(i256::from_i128(3000000_i128)),
4062                    None,
4063                    Some(i256::from_i128(5000000_i128))
4064                ]
4065            );
4066        }
4067
4068        // test i8 to decimal type with overflow the result type
4069        // the 100 will be converted to 1000_i128, but it is out of range for max value in the precision 3.
4070        let array = Int8Array::from(vec![1, 2, 3, 4, 100]);
4071        let array = Arc::new(array) as ArrayRef;
4072        let casted_array = cast(&array, &DataType::Decimal256(3, 1));
4073        assert!(casted_array.is_ok());
4074        let array = casted_array.unwrap();
4075        let array: &Decimal256Array = array.as_primitive();
4076        assert!(array.is_null(4));
4077
4078        // test f32 to decimal type
4079        let array = Float32Array::from(vec![
4080            Some(1.1),
4081            Some(2.2),
4082            Some(4.4),
4083            None,
4084            Some(1.123_456_4), // round down
4085            Some(1.123_456_7), // round up
4086        ]);
4087        generate_cast_test_case!(
4088            &array,
4089            Decimal256Array,
4090            &decimal_type,
4091            vec![
4092                Some(i256::from_i128(1100000_i128)),
4093                Some(i256::from_i128(2200000_i128)),
4094                Some(i256::from_i128(4400000_i128)),
4095                None,
4096                Some(i256::from_i128(1123456_i128)), // round down
4097                Some(i256::from_i128(1123457_i128)), // round up
4098            ]
4099        );
4100
4101        // test f64 to decimal type
4102        let array = Float64Array::from(vec![
4103            Some(1.1),
4104            Some(2.2),
4105            Some(4.4),
4106            None,
4107            Some(1.123_456_489_123_4),     // round down
4108            Some(1.123_456_789_123_4),     // round up
4109            Some(1.123_456_489_012_345_6), // round down
4110            Some(1.123_456_789_012_345_6), // round up
4111        ]);
4112        generate_cast_test_case!(
4113            &array,
4114            Decimal256Array,
4115            &decimal_type,
4116            vec![
4117                Some(i256::from_i128(1100000_i128)),
4118                Some(i256::from_i128(2200000_i128)),
4119                Some(i256::from_i128(4400000_i128)),
4120                None,
4121                Some(i256::from_i128(1123456_i128)), // round down
4122                Some(i256::from_i128(1123457_i128)), // round up
4123                Some(i256::from_i128(1123456_i128)), // round down
4124                Some(i256::from_i128(1123457_i128)), // round up
4125            ]
4126        );
4127    }
4128
4129    /// Checks the fast-path classification against `num_cast` for every pair of
4130    /// numeric types. `num_cast` fails only on values outside the target's range,
4131    /// so each type's extremes decide, plus NaN for floats.
4132    #[test]
4133    fn test_is_infallible_numeric_cast() {
4134        macro_rules! check {
4135            ($from:ty => $values:expr, [$($to:ty),*]) => {$(
4136                let infallible = is_infallible_numeric_cast(
4137                    <<$from as ArrowPrimitiveType>::Native as NumericNative>::KIND,
4138                    <<$to as ArrowPrimitiveType>::Native as NumericNative>::KIND,
4139                );
4140                let succeeds = $values
4141                    .iter()
4142                    .all(|&v| num_cast::<_, <$to as ArrowPrimitiveType>::Native>(v).is_some());
4143                assert_eq!(
4144                    infallible,
4145                    succeeds,
4146                    "{} to {}",
4147                    <$from as ArrowPrimitiveType>::DATA_TYPE,
4148                    <$to as ArrowPrimitiveType>::DATA_TYPE
4149                );
4150            )*};
4151        }
4152        macro_rules! check_all {
4153            ($($from:ty => $values:expr),* $(,)?) => {$(
4154                check!($from => $values, [
4155                    UInt8Type, UInt16Type, UInt32Type, UInt64Type, Int8Type, Int16Type,
4156                    Int32Type, Int64Type, Float16Type, Float32Type, Float64Type
4157                ]);
4158            )*};
4159        }
4160        check_all! {
4161            UInt8Type => [u8::MIN, u8::MAX],
4162            UInt16Type => [u16::MIN, u16::MAX],
4163            UInt32Type => [u32::MIN, u32::MAX],
4164            UInt64Type => [u64::MIN, u64::MAX],
4165            Int8Type => [i8::MIN, i8::MAX],
4166            Int16Type => [i16::MIN, i16::MAX],
4167            Int32Type => [i32::MIN, i32::MAX],
4168            Int64Type => [i64::MIN, i64::MAX],
4169            Float16Type => [f16::MIN, f16::MAX, f16::NAN],
4170            Float32Type => [f32::MIN, f32::MAX, f32::NAN],
4171            Float64Type => [f64::MIN, f64::MAX, f64::NAN],
4172        }
4173    }
4174
4175    #[test]
4176    fn test_cast_i32_to_f64() {
4177        let array = Int32Array::from(vec![5, 6, 7, 8, 9]);
4178        let b = cast(&array, &DataType::Float64).unwrap();
4179        let c = b.as_primitive::<Float64Type>();
4180        assert_eq!(5.0, c.value(0));
4181        assert_eq!(6.0, c.value(1));
4182        assert_eq!(7.0, c.value(2));
4183        assert_eq!(8.0, c.value(3));
4184        assert_eq!(9.0, c.value(4));
4185    }
4186
4187    #[test]
4188    fn test_cast_i32_to_u8() {
4189        let array = Int32Array::from(vec![-5, 6, -7, 8, 100000000]);
4190        let b = cast(&array, &DataType::UInt8).unwrap();
4191        let c = b.as_primitive::<UInt8Type>();
4192        assert!(!c.is_valid(0));
4193        assert_eq!(6, c.value(1));
4194        assert!(!c.is_valid(2));
4195        assert_eq!(8, c.value(3));
4196        // overflows return None
4197        assert!(!c.is_valid(4));
4198    }
4199
4200    #[test]
4201    #[should_panic(expected = "Can't cast value -5 to type UInt8")]
4202    fn test_cast_int32_to_u8_with_error() {
4203        let array = Int32Array::from(vec![-5, 6, -7, 8, 100000000]);
4204        // overflow with the error
4205        let cast_option = CastOptions {
4206            safe: false,
4207            format_options: FormatOptions::default(),
4208        };
4209        let result = cast_with_options(&array, &DataType::UInt8, &cast_option);
4210        assert!(result.is_err());
4211        result.unwrap();
4212    }
4213
4214    #[test]
4215    fn test_cast_i32_to_u8_sliced() {
4216        let array = Int32Array::from(vec![-5, 6, -7, 8, 100000000]);
4217        assert_eq!(0, array.offset());
4218        let array = array.slice(2, 3);
4219        let b = cast(&array, &DataType::UInt8).unwrap();
4220        assert_eq!(3, b.len());
4221        let c = b.as_primitive::<UInt8Type>();
4222        assert!(!c.is_valid(0));
4223        assert_eq!(8, c.value(1));
4224        // overflows return None
4225        assert!(!c.is_valid(2));
4226    }
4227
4228    #[test]
4229    fn test_cast_i32_to_i32() {
4230        let array = Int32Array::from(vec![5, 6, 7, 8, 9]);
4231        let b = cast(&array, &DataType::Int32).unwrap();
4232        let c = b.as_primitive::<Int32Type>();
4233        assert_eq!(5, c.value(0));
4234        assert_eq!(6, c.value(1));
4235        assert_eq!(7, c.value(2));
4236        assert_eq!(8, c.value(3));
4237        assert_eq!(9, c.value(4));
4238    }
4239
4240    #[test]
4241    fn test_cast_int_to_utf8view() {
4242        let inputs = vec![
4243            Arc::new(Int8Array::from(vec![None, Some(8), Some(9), Some(10)])) as ArrayRef,
4244            Arc::new(Int16Array::from(vec![None, Some(8), Some(9), Some(10)])) as ArrayRef,
4245            Arc::new(Int32Array::from(vec![None, Some(8), Some(9), Some(10)])) as ArrayRef,
4246            Arc::new(Int64Array::from(vec![None, Some(8), Some(9), Some(10)])) as ArrayRef,
4247            Arc::new(UInt8Array::from(vec![None, Some(8), Some(9), Some(10)])) as ArrayRef,
4248            Arc::new(UInt16Array::from(vec![None, Some(8), Some(9), Some(10)])) as ArrayRef,
4249            Arc::new(UInt32Array::from(vec![None, Some(8), Some(9), Some(10)])) as ArrayRef,
4250            Arc::new(UInt64Array::from(vec![None, Some(8), Some(9), Some(10)])) as ArrayRef,
4251        ];
4252        let expected: ArrayRef = Arc::new(StringViewArray::from(vec![
4253            None,
4254            Some("8"),
4255            Some("9"),
4256            Some("10"),
4257        ]));
4258
4259        for array in inputs {
4260            assert!(can_cast_types(array.data_type(), &DataType::Utf8View));
4261            let arr = cast(&array, &DataType::Utf8View).unwrap();
4262            assert_eq!(expected.as_ref(), arr.as_ref());
4263        }
4264    }
4265
4266    #[test]
4267    #[cfg_attr(miri, ignore)] // Unsupported inline assembly
4268    fn test_cast_float_to_utf8view() {
4269        let inputs = vec![
4270            Arc::new(Float16Array::from(vec![
4271                Some(f16::from_f64(1.5)),
4272                Some(f16::from_f64(2.5)),
4273                None,
4274            ])) as ArrayRef,
4275            Arc::new(Float32Array::from(vec![Some(1.5), Some(2.5), None])) as ArrayRef,
4276            Arc::new(Float64Array::from(vec![Some(1.5), Some(2.5), None])) as ArrayRef,
4277        ];
4278
4279        let expected: ArrayRef =
4280            Arc::new(StringViewArray::from(vec![Some("1.5"), Some("2.5"), None]));
4281
4282        for array in inputs {
4283            assert!(can_cast_types(array.data_type(), &DataType::Utf8View));
4284            let arr = cast(&array, &DataType::Utf8View).unwrap();
4285            assert_eq!(expected.as_ref(), arr.as_ref());
4286        }
4287    }
4288
4289    #[test]
4290    fn test_cast_utf8_to_i32() {
4291        let array = StringArray::from(vec!["5", "6", "seven", "8", "9.1"]);
4292        let b = cast(&array, &DataType::Int32).unwrap();
4293        let c = b.as_primitive::<Int32Type>();
4294        assert_eq!(5, c.value(0));
4295        assert_eq!(6, c.value(1));
4296        assert!(!c.is_valid(2));
4297        assert_eq!(8, c.value(3));
4298        assert!(!c.is_valid(4));
4299    }
4300
4301    #[test]
4302    fn test_cast_utf8view_to_i32() {
4303        let array = StringViewArray::from(vec!["5", "6", "seven", "8", "9.1"]);
4304        let b = cast(&array, &DataType::Int32).unwrap();
4305        let c = b.as_primitive::<Int32Type>();
4306        assert_eq!(5, c.value(0));
4307        assert_eq!(6, c.value(1));
4308        assert!(!c.is_valid(2));
4309        assert_eq!(8, c.value(3));
4310        assert!(!c.is_valid(4));
4311    }
4312
4313    #[test]
4314    fn test_cast_utf8view_to_f32() {
4315        let array = StringViewArray::from(vec!["3", "4.56", "seven", "8.9"]);
4316        let b = cast(&array, &DataType::Float32).unwrap();
4317        let c = b.as_primitive::<Float32Type>();
4318        assert_eq!(3.0, c.value(0));
4319        assert_eq!(4.56, c.value(1));
4320        assert!(!c.is_valid(2));
4321        assert_eq!(8.9, c.value(3));
4322    }
4323
4324    #[test]
4325    #[cfg_attr(miri, ignore)] // Unsupported inline assembly
4326    fn test_cast_string_to_f16() {
4327        let arrays = [
4328            Arc::new(StringViewArray::from(vec!["3", "4.56", "seven", "8.9"])) as ArrayRef,
4329            Arc::new(StringArray::from(vec!["3", "4.56", "seven", "8.9"])),
4330            Arc::new(LargeStringArray::from(vec!["3", "4.56", "seven", "8.9"])),
4331        ];
4332        for array in arrays {
4333            let b = cast(&array, &DataType::Float16).unwrap();
4334            let c = b.as_primitive::<Float16Type>();
4335            assert_eq!(half::f16::from_f32(3.0), c.value(0));
4336            assert_eq!(half::f16::from_f32(4.56), c.value(1));
4337            assert!(!c.is_valid(2));
4338            assert_eq!(half::f16::from_f32(8.9), c.value(3));
4339        }
4340    }
4341
4342    #[test]
4343    fn test_cast_utf8view_to_decimal128() {
4344        let array = StringViewArray::from(vec![None, Some("4"), Some("5.6"), Some("7.89")]);
4345        let arr = Arc::new(array) as ArrayRef;
4346        generate_cast_test_case!(
4347            &arr,
4348            Decimal128Array,
4349            &DataType::Decimal128(4, 2),
4350            vec![None, Some(400_i128), Some(560_i128), Some(789_i128)]
4351        );
4352    }
4353
4354    #[test]
4355    fn test_cast_with_options_utf8_to_i32() {
4356        let array = StringArray::from(vec!["5", "6", "seven", "8", "9.1"]);
4357        let result = cast_with_options(
4358            &array,
4359            &DataType::Int32,
4360            &CastOptions {
4361                safe: false,
4362                format_options: FormatOptions::default(),
4363            },
4364        );
4365        match result {
4366            Ok(_) => panic!("expected error"),
4367            Err(e) => {
4368                assert!(
4369                    e.to_string()
4370                        .contains("Cast error: Cannot cast string 'seven' to value of Int32 type",),
4371                    "Error: {e}"
4372                )
4373            }
4374        }
4375    }
4376
4377    #[test]
4378    fn test_cast_utf8_to_bool() {
4379        let strings = StringArray::from(vec!["true", "false", "invalid", " Y ", ""]);
4380        let casted = cast(&strings, &DataType::Boolean).unwrap();
4381        let expected = BooleanArray::from(vec![Some(true), Some(false), None, Some(true), None]);
4382        assert_eq!(*as_boolean_array(&casted), expected);
4383    }
4384
4385    #[test]
4386    fn test_cast_utf8view_to_bool() {
4387        let strings = StringViewArray::from(vec!["true", "false", "invalid", " Y ", ""]);
4388        let casted = cast(&strings, &DataType::Boolean).unwrap();
4389        let expected = BooleanArray::from(vec![Some(true), Some(false), None, Some(true), None]);
4390        assert_eq!(*as_boolean_array(&casted), expected);
4391    }
4392
4393    #[test]
4394    fn test_cast_with_options_utf8_to_bool() {
4395        let strings = StringArray::from(vec!["true", "false", "invalid", " Y ", ""]);
4396        let casted = cast_with_options(
4397            &strings,
4398            &DataType::Boolean,
4399            &CastOptions {
4400                safe: false,
4401                format_options: FormatOptions::default(),
4402            },
4403        );
4404        match casted {
4405            Ok(_) => panic!("expected error"),
4406            Err(e) => {
4407                assert!(
4408                    e.to_string().contains(
4409                        "Cast error: Cannot cast value 'invalid' to value of Boolean type"
4410                    )
4411                )
4412            }
4413        }
4414    }
4415
4416    #[test]
4417    fn test_cast_bool_to_i32() {
4418        let array = BooleanArray::from(vec![Some(true), Some(false), None]);
4419        let b = cast(&array, &DataType::Int32).unwrap();
4420        let c = b.as_primitive::<Int32Type>();
4421        assert_eq!(1, c.value(0));
4422        assert_eq!(0, c.value(1));
4423        assert!(!c.is_valid(2));
4424    }
4425
4426    #[test]
4427    fn test_cast_bool_numeric_sliced() {
4428        for nulls in [
4429            None,
4430            Some(NullBuffer::from(
4431                [false, true, true, false, true, true].repeat(12),
4432            )),
4433            Some(NullBuffer::new_null(72)),
4434        ] {
4435            // Include true values under nulls and slices crossing a bitmap word boundary.
4436            let booleans = BooleanArray::new(
4437                BooleanBuffer::from([true, false, true, false, true, false].repeat(12)),
4438                nulls.clone(),
4439            );
4440            let numbers = Int32Array::new([1, 0, 1, 0, 1, 0].repeat(12).into(), nulls);
4441            for data_type in [
4442                Int8, Int16, Int32, Int64, UInt8, UInt16, UInt32, UInt64, Float16, Float32, Float64,
4443            ] {
4444                let expected = cast(&numbers, &data_type).unwrap();
4445                for offset in [0, 3, 63, 72] {
4446                    let input = booleans.slice(offset, 72 - offset);
4447                    let expected = expected.slice(offset, 72 - offset);
4448                    let actual = cast(&input, &data_type).unwrap();
4449                    assert_eq!(actual.as_ref(), expected.as_ref());
4450
4451                    let actual = cast(expected.as_ref(), &Boolean).unwrap();
4452                    assert_eq!(actual.as_ref(), &input);
4453                }
4454            }
4455        }
4456    }
4457
4458    #[test]
4459    fn test_cast_float_to_bool_special_values() {
4460        let numbers = Float64Array::from(vec![
4461            0.0,
4462            -0.0,
4463            1.5,
4464            -1.5,
4465            f64::NAN,
4466            f64::INFINITY,
4467            f64::NEG_INFINITY,
4468        ]);
4469        let expected = BooleanArray::from(vec![false, false, true, true, true, true, true]);
4470        for data_type in [Float16, Float32, Float64] {
4471            let input = cast(&numbers, &data_type).unwrap();
4472            let actual = cast(input.as_ref(), &Boolean).unwrap();
4473            assert_eq!(actual.as_ref(), &expected);
4474        }
4475    }
4476
4477    #[test]
4478    fn test_cast_bool_to_string() {
4479        for nulls in [
4480            None,
4481            Some(NullBuffer::from([false, false, true, true].repeat(18))),
4482            Some(NullBuffer::new_null(72)),
4483        ] {
4484            // Include both Boolean values under nulls, an unaligned slice, and an empty slice.
4485            let array = BooleanArray::new(BooleanBuffer::from([true, false].repeat(36)), nulls);
4486            let expected: Vec<_> = ["true", "false"]
4487                .repeat(36)
4488                .into_iter()
4489                .enumerate()
4490                .map(|(i, value)| array.is_valid(i).then_some(value))
4491                .collect();
4492            for (offset, len) in [(0, 72), (3, 65), (72, 0)] {
4493                let input = array.slice(offset, len);
4494                for data_type in [Utf8, LargeUtf8, Utf8View] {
4495                    let actual = cast(&input, &data_type).unwrap();
4496                    let values: Vec<_> = match data_type {
4497                        Utf8 => actual.as_string::<i32>().iter().collect(),
4498                        LargeUtf8 => actual.as_string::<i64>().iter().collect(),
4499                        Utf8View => actual.as_string_view().iter().collect(),
4500                        _ => unreachable!(),
4501                    };
4502                    assert_eq!(values, expected[offset..offset + len]);
4503                }
4504            }
4505        }
4506    }
4507
4508    #[test]
4509    fn test_cast_bool_to_f64() {
4510        let array = BooleanArray::from(vec![Some(true), Some(false), None]);
4511        let b = cast(&array, &DataType::Float64).unwrap();
4512        let c = b.as_primitive::<Float64Type>();
4513        assert_eq!(1.0, c.value(0));
4514        assert_eq!(0.0, c.value(1));
4515        assert!(!c.is_valid(2));
4516    }
4517
4518    #[test]
4519    fn test_cast_integer_to_timestamp() {
4520        let array = Int64Array::from(vec![Some(2), Some(10), None]);
4521        let expected = cast(&array, &DataType::Timestamp(TimeUnit::Microsecond, None)).unwrap();
4522
4523        let array = Int8Array::from(vec![Some(2), Some(10), None]);
4524        let actual = cast(&array, &DataType::Timestamp(TimeUnit::Microsecond, None)).unwrap();
4525
4526        assert_eq!(&actual, &expected);
4527
4528        let array = Int16Array::from(vec![Some(2), Some(10), None]);
4529        let actual = cast(&array, &DataType::Timestamp(TimeUnit::Microsecond, None)).unwrap();
4530
4531        assert_eq!(&actual, &expected);
4532
4533        let array = Int32Array::from(vec![Some(2), Some(10), None]);
4534        let actual = cast(&array, &DataType::Timestamp(TimeUnit::Microsecond, None)).unwrap();
4535
4536        assert_eq!(&actual, &expected);
4537
4538        let array = UInt8Array::from(vec![Some(2), Some(10), None]);
4539        let actual = cast(&array, &DataType::Timestamp(TimeUnit::Microsecond, None)).unwrap();
4540
4541        assert_eq!(&actual, &expected);
4542
4543        let array = UInt16Array::from(vec![Some(2), Some(10), None]);
4544        let actual = cast(&array, &DataType::Timestamp(TimeUnit::Microsecond, None)).unwrap();
4545
4546        assert_eq!(&actual, &expected);
4547
4548        let array = UInt32Array::from(vec![Some(2), Some(10), None]);
4549        let actual = cast(&array, &DataType::Timestamp(TimeUnit::Microsecond, None)).unwrap();
4550
4551        assert_eq!(&actual, &expected);
4552
4553        let array = UInt64Array::from(vec![Some(2), Some(10), None]);
4554        let actual = cast(&array, &DataType::Timestamp(TimeUnit::Microsecond, None)).unwrap();
4555
4556        assert_eq!(&actual, &expected);
4557    }
4558
4559    #[test]
4560    fn test_cast_timestamp_to_integer() {
4561        let array = TimestampMillisecondArray::from(vec![Some(5), Some(1), None])
4562            .with_timezone("UTC".to_string());
4563        let expected = cast(&array, &DataType::Int64).unwrap();
4564
4565        let actual = cast(&cast(&array, &DataType::Int8).unwrap(), &DataType::Int64).unwrap();
4566        assert_eq!(&actual, &expected);
4567
4568        let actual = cast(&cast(&array, &DataType::Int16).unwrap(), &DataType::Int64).unwrap();
4569        assert_eq!(&actual, &expected);
4570
4571        let actual = cast(&cast(&array, &DataType::Int32).unwrap(), &DataType::Int64).unwrap();
4572        assert_eq!(&actual, &expected);
4573
4574        let actual = cast(&cast(&array, &DataType::UInt8).unwrap(), &DataType::Int64).unwrap();
4575        assert_eq!(&actual, &expected);
4576
4577        let actual = cast(&cast(&array, &DataType::UInt16).unwrap(), &DataType::Int64).unwrap();
4578        assert_eq!(&actual, &expected);
4579
4580        let actual = cast(&cast(&array, &DataType::UInt32).unwrap(), &DataType::Int64).unwrap();
4581        assert_eq!(&actual, &expected);
4582
4583        let actual = cast(&cast(&array, &DataType::UInt64).unwrap(), &DataType::Int64).unwrap();
4584        assert_eq!(&actual, &expected);
4585    }
4586
4587    #[test]
4588    #[cfg_attr(miri, ignore)] // Unsupported inline assembly
4589    fn test_cast_floating_to_timestamp() {
4590        let array = Int64Array::from(vec![Some(2), Some(10), None]);
4591        let expected = cast(&array, &DataType::Timestamp(TimeUnit::Microsecond, None)).unwrap();
4592
4593        let array = Float16Array::from(vec![
4594            Some(f16::from_f32(2.0)),
4595            Some(f16::from_f32(10.6)),
4596            None,
4597        ]);
4598        let actual = cast(&array, &DataType::Timestamp(TimeUnit::Microsecond, None)).unwrap();
4599
4600        assert_eq!(&actual, &expected);
4601
4602        let array = Float32Array::from(vec![Some(2.0), Some(10.6), None]);
4603        let actual = cast(&array, &DataType::Timestamp(TimeUnit::Microsecond, None)).unwrap();
4604
4605        assert_eq!(&actual, &expected);
4606
4607        let array = Float64Array::from(vec![Some(2.1), Some(10.2), None]);
4608        let actual = cast(&array, &DataType::Timestamp(TimeUnit::Microsecond, None)).unwrap();
4609
4610        assert_eq!(&actual, &expected);
4611    }
4612
4613    #[test]
4614    #[cfg_attr(miri, ignore)] // Unsupported inline assembly
4615    fn test_cast_timestamp_to_floating() {
4616        let array = TimestampMillisecondArray::from(vec![Some(5), Some(1), None])
4617            .with_timezone("UTC".to_string());
4618        let expected = cast(&array, &DataType::Int64).unwrap();
4619
4620        let actual = cast(&cast(&array, &DataType::Float16).unwrap(), &DataType::Int64).unwrap();
4621        assert_eq!(&actual, &expected);
4622
4623        let actual = cast(&cast(&array, &DataType::Float32).unwrap(), &DataType::Int64).unwrap();
4624        assert_eq!(&actual, &expected);
4625
4626        let actual = cast(&cast(&array, &DataType::Float64).unwrap(), &DataType::Int64).unwrap();
4627        assert_eq!(&actual, &expected);
4628    }
4629
4630    #[test]
4631    fn test_cast_decimal_to_timestamp() {
4632        let array = Int64Array::from(vec![Some(2), Some(10), None]);
4633        let expected = cast(&array, &DataType::Timestamp(TimeUnit::Microsecond, None)).unwrap();
4634
4635        let array = Decimal128Array::from(vec![Some(200), Some(1000), None])
4636            .with_precision_and_scale(4, 2)
4637            .unwrap();
4638        let actual = cast(&array, &DataType::Timestamp(TimeUnit::Microsecond, None)).unwrap();
4639
4640        assert_eq!(&actual, &expected);
4641
4642        let array = Decimal256Array::from(vec![
4643            Some(i256::from_i128(2000)),
4644            Some(i256::from_i128(10000)),
4645            None,
4646        ])
4647        .with_precision_and_scale(5, 3)
4648        .unwrap();
4649        let actual = cast(&array, &DataType::Timestamp(TimeUnit::Microsecond, None)).unwrap();
4650
4651        assert_eq!(&actual, &expected);
4652    }
4653
4654    #[test]
4655    fn test_cast_timestamp_to_decimal() {
4656        let array = TimestampMillisecondArray::from(vec![Some(5), Some(1), None])
4657            .with_timezone("UTC".to_string());
4658        let expected = cast(&array, &DataType::Int64).unwrap();
4659
4660        let actual = cast(
4661            &cast(&array, &DataType::Decimal128(5, 2)).unwrap(),
4662            &DataType::Int64,
4663        )
4664        .unwrap();
4665        assert_eq!(&actual, &expected);
4666
4667        let actual = cast(
4668            &cast(&array, &DataType::Decimal256(10, 5)).unwrap(),
4669            &DataType::Int64,
4670        )
4671        .unwrap();
4672        assert_eq!(&actual, &expected);
4673    }
4674
4675    #[test]
4676    fn test_cast_date32_to_date64() {
4677        let a = Date32Array::from(vec![10000, 17890]);
4678        let array = Arc::new(a) as ArrayRef;
4679        let b = cast(&array, &DataType::Date64).unwrap();
4680        let c = b.as_primitive::<Date64Type>();
4681        assert_eq!(864000000000, c.value(0));
4682        assert_eq!(1545696000000, c.value(1));
4683    }
4684
4685    #[test]
4686    fn test_cast_date64_to_date32() {
4687        let a = Date64Array::from(vec![Some(864000000005), Some(1545696000001), None]);
4688        let array = Arc::new(a) as ArrayRef;
4689        let b = cast(&array, &DataType::Date32).unwrap();
4690        let c = b.as_primitive::<Date32Type>();
4691        assert_eq!(10000, c.value(0));
4692        assert_eq!(17890, c.value(1));
4693        assert!(c.is_null(2));
4694    }
4695
4696    #[test]
4697    fn test_cast_date64_to_date32_overflow() {
4698        let a = Date64Array::from(vec![i64::MAX]);
4699        let array = Arc::new(a) as ArrayRef;
4700
4701        let b = cast(&array, &DataType::Date32).unwrap();
4702        let c = b.as_primitive::<Date32Type>();
4703        assert!(c.is_null(0));
4704
4705        let options = CastOptions {
4706            safe: false,
4707            ..Default::default()
4708        };
4709        let err = cast_with_options(&array, &DataType::Date32, &options).unwrap_err();
4710        assert!(
4711            err.to_string().contains("Cannot cast Date64 value"),
4712            "{err}"
4713        );
4714    }
4715
4716    #[test]
4717    fn test_cast_string_to_integral_overflow() {
4718        let str = Arc::new(StringArray::from(vec![
4719            Some("123"),
4720            Some("-123"),
4721            Some("86374"),
4722            Some("-40000"),
4723            None,
4724        ])) as ArrayRef;
4725
4726        let options = CastOptions {
4727            safe: true,
4728            format_options: FormatOptions::default(),
4729        };
4730        let res = cast_with_options(&str, &DataType::Int16, &options).expect("should cast to i16");
4731        let expected = Arc::new(Int16Array::from(vec![
4732            Some(123),
4733            Some(-123),
4734            None,
4735            None,
4736            None,
4737        ])) as ArrayRef;
4738        assert_eq!(&res, &expected);
4739    }
4740
4741    #[test]
4742    fn test_cast_string_to_timestamp() {
4743        let a0 = Arc::new(StringViewArray::from(vec![
4744            Some("2020-09-08T12:00:00.123456789+00:00"),
4745            Some("Not a valid date"),
4746            None,
4747        ])) as ArrayRef;
4748        let a1 = Arc::new(StringArray::from(vec![
4749            Some("2020-09-08T12:00:00.123456789+00:00"),
4750            Some("Not a valid date"),
4751            None,
4752        ])) as ArrayRef;
4753        let a2 = Arc::new(LargeStringArray::from(vec![
4754            Some("2020-09-08T12:00:00.123456789+00:00"),
4755            Some("Not a valid date"),
4756            None,
4757        ])) as ArrayRef;
4758        for array in &[a0, a1, a2] {
4759            for time_unit in &[
4760                TimeUnit::Second,
4761                TimeUnit::Millisecond,
4762                TimeUnit::Microsecond,
4763                TimeUnit::Nanosecond,
4764            ] {
4765                let to_type = DataType::Timestamp(*time_unit, None);
4766                let b = cast(array, &to_type).unwrap();
4767
4768                match time_unit {
4769                    TimeUnit::Second => {
4770                        let c = b.as_primitive::<TimestampSecondType>();
4771                        assert_eq!(1599566400, c.value(0));
4772                        assert!(c.is_null(1));
4773                        assert!(c.is_null(2));
4774                    }
4775                    TimeUnit::Millisecond => {
4776                        let c = b
4777                            .as_any()
4778                            .downcast_ref::<TimestampMillisecondArray>()
4779                            .unwrap();
4780                        assert_eq!(1599566400123, c.value(0));
4781                        assert!(c.is_null(1));
4782                        assert!(c.is_null(2));
4783                    }
4784                    TimeUnit::Microsecond => {
4785                        let c = b
4786                            .as_any()
4787                            .downcast_ref::<TimestampMicrosecondArray>()
4788                            .unwrap();
4789                        assert_eq!(1599566400123456, c.value(0));
4790                        assert!(c.is_null(1));
4791                        assert!(c.is_null(2));
4792                    }
4793                    TimeUnit::Nanosecond => {
4794                        let c = b
4795                            .as_any()
4796                            .downcast_ref::<TimestampNanosecondArray>()
4797                            .unwrap();
4798                        assert_eq!(1599566400123456789, c.value(0));
4799                        assert!(c.is_null(1));
4800                        assert!(c.is_null(2));
4801                    }
4802                }
4803
4804                let options = CastOptions {
4805                    safe: false,
4806                    format_options: FormatOptions::default(),
4807                };
4808                let err = cast_with_options(array, &to_type, &options).unwrap_err();
4809                assert_eq!(
4810                    err.to_string(),
4811                    "Parser error: Error parsing timestamp from 'Not a valid date': error parsing date"
4812                );
4813            }
4814        }
4815    }
4816
4817    #[test]
4818    fn test_cast_string_to_timestamp_overflow() {
4819        let array = StringArray::from(vec!["9800-09-08T12:00:00.123456789"]);
4820        let result = cast(&array, &DataType::Timestamp(TimeUnit::Second, None)).unwrap();
4821        let result = result.as_primitive::<TimestampSecondType>();
4822        assert_eq!(result.values(), &[247112596800]);
4823    }
4824
4825    #[test]
4826    fn test_cast_string_to_date32_with_surrounding_whitespace() {
4827        let array = StringArray::from(vec![" 2026-09-29 ", "2026-09-29"]);
4828
4829        let result = cast(&array, &DataType::Date32).unwrap();
4830        let result = result.as_primitive::<Date32Type>();
4831
4832        assert!(!result.is_null(0));
4833        assert_eq!(result.value(0), result.value(1));
4834    }
4835
4836    #[test]
4837    fn test_cast_string_to_date32() {
4838        let a0 = Arc::new(StringViewArray::from(vec![
4839            Some("2018-12-25"),
4840            Some("Not a valid date"),
4841            None,
4842        ])) as ArrayRef;
4843        let a1 = Arc::new(StringArray::from(vec![
4844            Some("2018-12-25"),
4845            Some("Not a valid date"),
4846            None,
4847        ])) as ArrayRef;
4848        let a2 = Arc::new(LargeStringArray::from(vec![
4849            Some("2018-12-25"),
4850            Some("Not a valid date"),
4851            None,
4852        ])) as ArrayRef;
4853        for array in &[a0, a1, a2] {
4854            let to_type = DataType::Date32;
4855            let b = cast(array, &to_type).unwrap();
4856            let c = b.as_primitive::<Date32Type>();
4857            assert_eq!(17890, c.value(0));
4858            assert!(c.is_null(1));
4859            assert!(c.is_null(2));
4860
4861            let options = CastOptions {
4862                safe: false,
4863                format_options: FormatOptions::default(),
4864            };
4865            let err = cast_with_options(array, &to_type, &options).unwrap_err();
4866            assert_eq!(
4867                err.to_string(),
4868                "Cast error: Cannot cast string 'Not a valid date' to value of Date32 type"
4869            );
4870        }
4871    }
4872
4873    #[test]
4874    fn test_cast_string_with_large_date_to_date32() {
4875        let array = Arc::new(StringArray::from(vec![
4876            Some("+10999-12-31"),
4877            Some("-0010-02-28"),
4878            Some("0010-02-28"),
4879            Some("0000-01-01"),
4880            Some("-0000-01-01"),
4881            Some("-0001-01-01"),
4882        ])) as ArrayRef;
4883        let to_type = DataType::Date32;
4884        let options = CastOptions {
4885            safe: false,
4886            format_options: FormatOptions::default(),
4887        };
4888        let b = cast_with_options(&array, &to_type, &options).unwrap();
4889        let c = b.as_primitive::<Date32Type>();
4890        assert_eq!(3298139, c.value(0)); // 10999-12-31
4891        assert_eq!(-723122, c.value(1)); // -0010-02-28
4892        assert_eq!(-715817, c.value(2)); // 0010-02-28
4893        assert_eq!(c.value(3), c.value(4)); // Expect 0000-01-01 and -0000-01-01 to be parsed the same
4894        assert_eq!(-719528, c.value(3)); // 0000-01-01
4895        assert_eq!(-719528, c.value(4)); // -0000-01-01
4896        assert_eq!(-719893, c.value(5)); // -0001-01-01
4897    }
4898
4899    #[test]
4900    fn test_cast_invalid_string_with_large_date_to_date32() {
4901        // Large dates need to be prefixed with a + or - sign, otherwise they are not parsed correctly
4902        let array = Arc::new(StringArray::from(vec![Some("10999-12-31")])) as ArrayRef;
4903        let to_type = DataType::Date32;
4904        let options = CastOptions {
4905            safe: false,
4906            format_options: FormatOptions::default(),
4907        };
4908        let err = cast_with_options(&array, &to_type, &options).unwrap_err();
4909        assert_eq!(
4910            err.to_string(),
4911            "Cast error: Cannot cast string '10999-12-31' to value of Date32 type"
4912        );
4913    }
4914
4915    #[test]
4916    fn test_cast_string_format_yyyymmdd_to_date32() {
4917        let a0 = Arc::new(StringViewArray::from(vec![
4918            Some("2020-12-25"),
4919            Some("20201117"),
4920        ])) as ArrayRef;
4921        let a1 = Arc::new(StringArray::from(vec![
4922            Some("2020-12-25"),
4923            Some("20201117"),
4924        ])) as ArrayRef;
4925        let a2 = Arc::new(LargeStringArray::from(vec![
4926            Some("2020-12-25"),
4927            Some("20201117"),
4928        ])) as ArrayRef;
4929
4930        for array in &[a0, a1, a2] {
4931            let to_type = DataType::Date32;
4932            let options = CastOptions {
4933                safe: false,
4934                format_options: FormatOptions::default(),
4935            };
4936            let result = cast_with_options(&array, &to_type, &options).unwrap();
4937            let c = result.as_primitive::<Date32Type>();
4938            assert_eq!(
4939                chrono::NaiveDate::from_ymd_opt(2020, 12, 25),
4940                c.value_as_date(0)
4941            );
4942            assert_eq!(
4943                chrono::NaiveDate::from_ymd_opt(2020, 11, 17),
4944                c.value_as_date(1)
4945            );
4946        }
4947    }
4948
4949    #[test]
4950    fn test_cast_string_to_time32second() {
4951        let a0 = Arc::new(StringViewArray::from(vec![
4952            Some("08:08:35.091323414"),
4953            Some("08:08:60.091323414"), // leap second
4954            Some("08:08:61.091323414"), // not valid
4955            Some("Not a valid time"),
4956            None,
4957        ])) as ArrayRef;
4958        let a1 = Arc::new(StringArray::from(vec![
4959            Some("08:08:35.091323414"),
4960            Some("08:08:60.091323414"), // leap second
4961            Some("08:08:61.091323414"), // not valid
4962            Some("Not a valid time"),
4963            None,
4964        ])) as ArrayRef;
4965        let a2 = Arc::new(LargeStringArray::from(vec![
4966            Some("08:08:35.091323414"),
4967            Some("08:08:60.091323414"), // leap second
4968            Some("08:08:61.091323414"), // not valid
4969            Some("Not a valid time"),
4970            None,
4971        ])) as ArrayRef;
4972        for array in &[a0, a1, a2] {
4973            let to_type = DataType::Time32(TimeUnit::Second);
4974            let b = cast(array, &to_type).unwrap();
4975            let c = b.as_primitive::<Time32SecondType>();
4976            assert_eq!(29315, c.value(0));
4977            assert_eq!(29340, c.value(1));
4978            assert!(c.is_null(2));
4979            assert!(c.is_null(3));
4980            assert!(c.is_null(4));
4981
4982            let options = CastOptions {
4983                safe: false,
4984                format_options: FormatOptions::default(),
4985            };
4986            let err = cast_with_options(array, &to_type, &options).unwrap_err();
4987            assert_eq!(
4988                err.to_string(),
4989                "Cast error: Cannot cast string '08:08:61.091323414' to value of Time32(s) type"
4990            );
4991        }
4992    }
4993
4994    #[test]
4995    fn test_cast_string_to_time32millisecond() {
4996        let a0 = Arc::new(StringViewArray::from(vec![
4997            Some("08:08:35.091323414"),
4998            Some("08:08:60.091323414"), // leap second
4999            Some("08:08:61.091323414"), // not valid
5000            Some("Not a valid time"),
5001            None,
5002        ])) as ArrayRef;
5003        let a1 = Arc::new(StringArray::from(vec![
5004            Some("08:08:35.091323414"),
5005            Some("08:08:60.091323414"), // leap second
5006            Some("08:08:61.091323414"), // not valid
5007            Some("Not a valid time"),
5008            None,
5009        ])) as ArrayRef;
5010        let a2 = Arc::new(LargeStringArray::from(vec![
5011            Some("08:08:35.091323414"),
5012            Some("08:08:60.091323414"), // leap second
5013            Some("08:08:61.091323414"), // not valid
5014            Some("Not a valid time"),
5015            None,
5016        ])) as ArrayRef;
5017        for array in &[a0, a1, a2] {
5018            let to_type = DataType::Time32(TimeUnit::Millisecond);
5019            let b = cast(array, &to_type).unwrap();
5020            let c = b.as_primitive::<Time32MillisecondType>();
5021            assert_eq!(29315091, c.value(0));
5022            assert_eq!(29340091, c.value(1));
5023            assert!(c.is_null(2));
5024            assert!(c.is_null(3));
5025            assert!(c.is_null(4));
5026
5027            let options = CastOptions {
5028                safe: false,
5029                format_options: FormatOptions::default(),
5030            };
5031            let err = cast_with_options(array, &to_type, &options).unwrap_err();
5032            assert_eq!(
5033                err.to_string(),
5034                "Cast error: Cannot cast string '08:08:61.091323414' to value of Time32(ms) type"
5035            );
5036        }
5037    }
5038
5039    #[test]
5040    fn test_cast_string_to_time64microsecond() {
5041        let a0 = Arc::new(StringViewArray::from(vec![
5042            Some("08:08:35.091323414"),
5043            Some("Not a valid time"),
5044            None,
5045        ])) as ArrayRef;
5046        let a1 = Arc::new(StringArray::from(vec![
5047            Some("08:08:35.091323414"),
5048            Some("Not a valid time"),
5049            None,
5050        ])) as ArrayRef;
5051        let a2 = Arc::new(LargeStringArray::from(vec![
5052            Some("08:08:35.091323414"),
5053            Some("Not a valid time"),
5054            None,
5055        ])) as ArrayRef;
5056        for array in &[a0, a1, a2] {
5057            let to_type = DataType::Time64(TimeUnit::Microsecond);
5058            let b = cast(array, &to_type).unwrap();
5059            let c = b.as_primitive::<Time64MicrosecondType>();
5060            assert_eq!(29315091323, c.value(0));
5061            assert!(c.is_null(1));
5062            assert!(c.is_null(2));
5063
5064            let options = CastOptions {
5065                safe: false,
5066                format_options: FormatOptions::default(),
5067            };
5068            let err = cast_with_options(array, &to_type, &options).unwrap_err();
5069            assert_eq!(
5070                err.to_string(),
5071                "Cast error: Cannot cast string 'Not a valid time' to value of Time64(µs) type"
5072            );
5073        }
5074    }
5075
5076    #[test]
5077    fn test_cast_string_to_time64nanosecond() {
5078        let a0 = Arc::new(StringViewArray::from(vec![
5079            Some("08:08:35.091323414"),
5080            Some("Not a valid time"),
5081            None,
5082        ])) as ArrayRef;
5083        let a1 = Arc::new(StringArray::from(vec![
5084            Some("08:08:35.091323414"),
5085            Some("Not a valid time"),
5086            None,
5087        ])) as ArrayRef;
5088        let a2 = Arc::new(LargeStringArray::from(vec![
5089            Some("08:08:35.091323414"),
5090            Some("Not a valid time"),
5091            None,
5092        ])) as ArrayRef;
5093        for array in &[a0, a1, a2] {
5094            let to_type = DataType::Time64(TimeUnit::Nanosecond);
5095            let b = cast(array, &to_type).unwrap();
5096            let c = b.as_primitive::<Time64NanosecondType>();
5097            assert_eq!(29315091323414, c.value(0));
5098            assert!(c.is_null(1));
5099            assert!(c.is_null(2));
5100
5101            let options = CastOptions {
5102                safe: false,
5103                format_options: FormatOptions::default(),
5104            };
5105            let err = cast_with_options(array, &to_type, &options).unwrap_err();
5106            assert_eq!(
5107                err.to_string(),
5108                "Cast error: Cannot cast string 'Not a valid time' to value of Time64(ns) type"
5109            );
5110        }
5111    }
5112
5113    #[test]
5114    fn test_cast_string_to_date64() {
5115        let a0 = Arc::new(StringViewArray::from(vec![
5116            Some("2020-09-08T12:00:00"),
5117            Some("Not a valid date"),
5118            None,
5119        ])) as ArrayRef;
5120        let a1 = Arc::new(StringArray::from(vec![
5121            Some("2020-09-08T12:00:00"),
5122            Some("Not a valid date"),
5123            None,
5124        ])) as ArrayRef;
5125        let a2 = Arc::new(LargeStringArray::from(vec![
5126            Some("2020-09-08T12:00:00"),
5127            Some("Not a valid date"),
5128            None,
5129        ])) as ArrayRef;
5130        for array in &[a0, a1, a2] {
5131            let to_type = DataType::Date64;
5132            let b = cast(array, &to_type).unwrap();
5133            let c = b.as_primitive::<Date64Type>();
5134            assert_eq!(1599566400000, c.value(0));
5135            assert!(c.is_null(1));
5136            assert!(c.is_null(2));
5137
5138            let options = CastOptions {
5139                safe: false,
5140                format_options: FormatOptions::default(),
5141            };
5142            let err = cast_with_options(array, &to_type, &options).unwrap_err();
5143            assert_eq!(
5144                err.to_string(),
5145                "Cast error: Cannot cast string 'Not a valid date' to value of Date64 type"
5146            );
5147        }
5148    }
5149
5150    macro_rules! test_safe_string_to_interval {
5151        ($data_vec:expr, $interval_unit:expr, $array_ty:ty, $expect_vec:expr) => {
5152            let source_string_array = Arc::new(StringArray::from($data_vec.clone())) as ArrayRef;
5153
5154            let options = CastOptions {
5155                safe: true,
5156                format_options: FormatOptions::default(),
5157            };
5158
5159            let target_interval_array = cast_with_options(
5160                &source_string_array.clone(),
5161                &DataType::Interval($interval_unit),
5162                &options,
5163            )
5164            .unwrap()
5165            .as_any()
5166            .downcast_ref::<$array_ty>()
5167            .unwrap()
5168            .clone() as $array_ty;
5169
5170            let target_string_array =
5171                cast_with_options(&target_interval_array, &DataType::Utf8, &options)
5172                    .unwrap()
5173                    .as_any()
5174                    .downcast_ref::<StringArray>()
5175                    .unwrap()
5176                    .clone();
5177
5178            let expect_string_array = StringArray::from($expect_vec);
5179
5180            assert_eq!(target_string_array, expect_string_array);
5181
5182            let target_large_string_array =
5183                cast_with_options(&target_interval_array, &DataType::LargeUtf8, &options)
5184                    .unwrap()
5185                    .as_any()
5186                    .downcast_ref::<LargeStringArray>()
5187                    .unwrap()
5188                    .clone();
5189
5190            let expect_large_string_array = LargeStringArray::from($expect_vec);
5191
5192            assert_eq!(target_large_string_array, expect_large_string_array);
5193        };
5194    }
5195
5196    #[test]
5197    fn test_cast_string_to_interval_year_month() {
5198        test_safe_string_to_interval!(
5199            vec![
5200                Some("1 year 1 month"),
5201                Some("1.5 years 13 month"),
5202                Some("30 days"),
5203                Some("31 days"),
5204                Some("2 months 31 days"),
5205                Some("2 months 31 days 1 second"),
5206                Some("foobar"),
5207            ],
5208            IntervalUnit::YearMonth,
5209            IntervalYearMonthArray,
5210            vec![
5211                Some("1 years 1 mons"),
5212                Some("2 years 7 mons"),
5213                None,
5214                None,
5215                None,
5216                None,
5217                None,
5218            ]
5219        );
5220    }
5221
5222    #[test]
5223    fn test_cast_string_to_interval_day_time() {
5224        test_safe_string_to_interval!(
5225            vec![
5226                Some("1 year 1 month"),
5227                Some("1.5 years 13 month"),
5228                Some("30 days"),
5229                Some("1 day 2 second 3.5 milliseconds"),
5230                Some("foobar"),
5231            ],
5232            IntervalUnit::DayTime,
5233            IntervalDayTimeArray,
5234            vec![
5235                Some("390 days"),
5236                Some("930 days"),
5237                Some("30 days"),
5238                None,
5239                None,
5240            ]
5241        );
5242    }
5243
5244    #[test]
5245    fn test_cast_string_to_interval_month_day_nano() {
5246        test_safe_string_to_interval!(
5247            vec![
5248                Some("1 year 1 month 1 day"),
5249                None,
5250                Some("1.5 years 13 month 35 days 1.4 milliseconds"),
5251                Some("3 days"),
5252                Some("8 seconds"),
5253                None,
5254                Some("1 day 29800 milliseconds"),
5255                Some("3 months 1 second"),
5256                Some("6 minutes 120 second"),
5257                Some("2 years 39 months 9 days 19 hours 1 minute 83 seconds 399222 milliseconds"),
5258                Some("foobar"),
5259            ],
5260            IntervalUnit::MonthDayNano,
5261            IntervalMonthDayNanoArray,
5262            vec![
5263                Some("13 mons 1 days"),
5264                None,
5265                Some("31 mons 35 days 0.001400000 secs"),
5266                Some("3 days"),
5267                Some("8.000000000 secs"),
5268                None,
5269                Some("1 days 29.800000000 secs"),
5270                Some("3 mons 1.000000000 secs"),
5271                Some("8 mins"),
5272                Some("63 mons 9 days 19 hours 9 mins 2.222000000 secs"),
5273                None,
5274            ]
5275        );
5276    }
5277
5278    macro_rules! test_unsafe_string_to_interval_err {
5279        ($data_vec:expr, $interval_unit:expr, $error_msg:expr) => {
5280            let string_array = Arc::new(StringArray::from($data_vec.clone())) as ArrayRef;
5281            let options = CastOptions {
5282                safe: false,
5283                format_options: FormatOptions::default(),
5284            };
5285            let arrow_err = cast_with_options(
5286                &string_array.clone(),
5287                &DataType::Interval($interval_unit),
5288                &options,
5289            )
5290            .unwrap_err();
5291            assert_eq!($error_msg, arrow_err.to_string());
5292        };
5293    }
5294
5295    #[test]
5296    fn test_cast_string_to_interval_err() {
5297        test_unsafe_string_to_interval_err!(
5298            vec![Some("foobar")],
5299            IntervalUnit::YearMonth,
5300            r#"Parser error: Invalid input syntax for type interval: "foobar""#
5301        );
5302        test_unsafe_string_to_interval_err!(
5303            vec![Some("foobar")],
5304            IntervalUnit::DayTime,
5305            r#"Parser error: Invalid input syntax for type interval: "foobar""#
5306        );
5307        test_unsafe_string_to_interval_err!(
5308            vec![Some("foobar")],
5309            IntervalUnit::MonthDayNano,
5310            r#"Parser error: Invalid input syntax for type interval: "foobar""#
5311        );
5312        test_unsafe_string_to_interval_err!(
5313            vec![Some("2 months 31 days 1 second")],
5314            IntervalUnit::YearMonth,
5315            "Cast error: Cannot cast 2 months 31 days 1 second to IntervalYearMonth. Only year and month fields are allowed."
5316        );
5317        test_unsafe_string_to_interval_err!(
5318            vec![Some("1 day 1.5 milliseconds")],
5319            IntervalUnit::DayTime,
5320            "Cast error: Cannot cast 1 day 1.5 milliseconds to IntervalDayTime because the nanos part isn't multiple of milliseconds"
5321        );
5322
5323        // overflow
5324        test_unsafe_string_to_interval_err!(
5325            vec![Some(format!(
5326                "{} century {} year {} month",
5327                i64::MAX - 2,
5328                i64::MAX - 2,
5329                i64::MAX - 2
5330            ))],
5331            IntervalUnit::DayTime,
5332            format!(
5333                "Arithmetic overflow: Overflow happened on: {} * 100",
5334                i64::MAX - 2
5335            )
5336        );
5337        test_unsafe_string_to_interval_err!(
5338            vec![Some(format!(
5339                "{} year {} month {} day",
5340                i64::MAX - 2,
5341                i64::MAX - 2,
5342                i64::MAX - 2
5343            ))],
5344            IntervalUnit::MonthDayNano,
5345            format!(
5346                "Arithmetic overflow: Overflow happened on: {} * 12",
5347                i64::MAX - 2
5348            )
5349        );
5350    }
5351
5352    #[test]
5353    fn test_cast_binary_to_fixed_size_binary() {
5354        let bytes_1 = b"Hiiii".as_slice();
5355        let bytes_2 = b"Hello".as_slice();
5356
5357        let binary_data = vec![Some(bytes_1), Some(bytes_2), None];
5358        let a1 = Arc::new(BinaryArray::from(binary_data.clone())) as ArrayRef;
5359        let a2 = Arc::new(LargeBinaryArray::from(binary_data)) as ArrayRef;
5360
5361        let array_ref = cast(&a1, &DataType::FixedSizeBinary(5)).unwrap();
5362        let down_cast = array_ref
5363            .as_any()
5364            .downcast_ref::<FixedSizeBinaryArray>()
5365            .unwrap();
5366        assert_eq!(bytes_1, down_cast.value(0));
5367        assert_eq!(bytes_2, down_cast.value(1));
5368        assert!(down_cast.is_null(2));
5369
5370        let array_ref = cast(&a2, &DataType::FixedSizeBinary(5)).unwrap();
5371        let down_cast = array_ref
5372            .as_any()
5373            .downcast_ref::<FixedSizeBinaryArray>()
5374            .unwrap();
5375        assert_eq!(bytes_1, down_cast.value(0));
5376        assert_eq!(bytes_2, down_cast.value(1));
5377        assert!(down_cast.is_null(2));
5378
5379        // test error cases when the length of binary are not same
5380        let bytes_1 = b"Hi".as_slice();
5381        let bytes_2 = b"Hello".as_slice();
5382
5383        let binary_data = vec![Some(bytes_1), Some(bytes_2), None];
5384        let a1 = Arc::new(BinaryArray::from(binary_data.clone())) as ArrayRef;
5385        let a2 = Arc::new(LargeBinaryArray::from(binary_data)) as ArrayRef;
5386
5387        let array_ref = cast_with_options(
5388            &a1,
5389            &DataType::FixedSizeBinary(5),
5390            &CastOptions {
5391                safe: false,
5392                format_options: FormatOptions::default(),
5393            },
5394        );
5395        assert!(array_ref.is_err());
5396
5397        let array_ref = cast_with_options(
5398            &a2,
5399            &DataType::FixedSizeBinary(5),
5400            &CastOptions {
5401                safe: false,
5402                format_options: FormatOptions::default(),
5403            },
5404        );
5405        assert!(array_ref.is_err());
5406    }
5407
5408    #[test]
5409    fn test_fixed_size_binary_to_binary() {
5410        let bytes_1 = b"Hiiii".as_slice();
5411        let bytes_2 = b"Hello".as_slice();
5412
5413        let binary_data = vec![Some(bytes_1), Some(bytes_2), None];
5414        let a1 = Arc::new(FixedSizeBinaryArray::try_from(binary_data.clone()).unwrap()) as ArrayRef;
5415
5416        let array_ref = cast(&a1, &DataType::Binary).unwrap();
5417        let down_cast = array_ref.as_binary::<i32>();
5418        assert_eq!(bytes_1, down_cast.value(0));
5419        assert_eq!(bytes_2, down_cast.value(1));
5420        assert!(down_cast.is_null(2));
5421
5422        let array_ref = cast(&a1, &DataType::LargeBinary).unwrap();
5423        let down_cast = array_ref.as_binary::<i64>();
5424        assert_eq!(bytes_1, down_cast.value(0));
5425        assert_eq!(bytes_2, down_cast.value(1));
5426        assert!(down_cast.is_null(2));
5427
5428        let array_ref = cast(&a1, &DataType::BinaryView).unwrap();
5429        let down_cast = array_ref.as_binary_view();
5430        assert_eq!(bytes_1, down_cast.value(0));
5431        assert_eq!(bytes_2, down_cast.value(1));
5432        assert!(down_cast.is_null(2));
5433    }
5434
5435    #[test]
5436    fn test_numeric_to_binary() {
5437        let a = Int16Array::from(vec![Some(1), Some(511), None]);
5438
5439        let array_ref = cast(&a, &DataType::Binary).unwrap();
5440        let down_cast = array_ref.as_binary::<i32>();
5441        assert_eq!(&1_i16.to_le_bytes(), down_cast.value(0));
5442        assert_eq!(&511_i16.to_le_bytes(), down_cast.value(1));
5443        assert!(down_cast.is_null(2));
5444
5445        let a = Int64Array::from(vec![Some(-1), Some(123456789), None]);
5446
5447        let array_ref = cast(&a, &DataType::Binary).unwrap();
5448        let down_cast = array_ref.as_binary::<i32>();
5449        assert_eq!(&(-1_i64).to_le_bytes(), down_cast.value(0));
5450        assert_eq!(&123456789_i64.to_le_bytes(), down_cast.value(1));
5451        assert!(down_cast.is_null(2));
5452    }
5453
5454    #[test]
5455    fn test_numeric_to_large_binary() {
5456        let a = Int16Array::from(vec![Some(1), Some(511), None]);
5457
5458        let array_ref = cast(&a, &DataType::LargeBinary).unwrap();
5459        let down_cast = array_ref.as_binary::<i64>();
5460        assert_eq!(&1_i16.to_le_bytes(), down_cast.value(0));
5461        assert_eq!(&511_i16.to_le_bytes(), down_cast.value(1));
5462        assert!(down_cast.is_null(2));
5463
5464        let a = Int64Array::from(vec![Some(-1), Some(123456789), None]);
5465
5466        let array_ref = cast(&a, &DataType::LargeBinary).unwrap();
5467        let down_cast = array_ref.as_binary::<i64>();
5468        assert_eq!(&(-1_i64).to_le_bytes(), down_cast.value(0));
5469        assert_eq!(&123456789_i64.to_le_bytes(), down_cast.value(1));
5470        assert!(down_cast.is_null(2));
5471    }
5472
5473    #[test]
5474    fn test_cast_date32_to_int32() {
5475        let array = Date32Array::from(vec![10000, 17890]);
5476        let b = cast(&array, &DataType::Int32).unwrap();
5477        let c = b.as_primitive::<Int32Type>();
5478        assert_eq!(10000, c.value(0));
5479        assert_eq!(17890, c.value(1));
5480    }
5481
5482    #[test]
5483    fn test_cast_int32_to_date32() {
5484        let array = Int32Array::from(vec![10000, 17890]);
5485        let b = cast(&array, &DataType::Date32).unwrap();
5486        let c = b.as_primitive::<Date32Type>();
5487        assert_eq!(10000, c.value(0));
5488        assert_eq!(17890, c.value(1));
5489    }
5490
5491    /// Compares arithmetic casts with Chrono for representable dates, including
5492    /// negative and fractional boundaries, nulls, and nonzero-offset slices.
5493    fn check_timestamp_casts<T: ArrowTimestampType>() {
5494        use rand::rngs::StdRng;
5495        use rand::{RngExt, SeedableRng};
5496
5497        let units = time_unit_multiple(&T::UNIT);
5498        let around = |x: i64| [x - 1, x, x + 1, -x - 1, -x, -x + 1];
5499        let mut values = vec![i64::MIN, i64::MAX];
5500        for base in [0, 60, 3_600, 86_400] {
5501            for seconds in around(base) {
5502                for fraction in [-1, 0, 1, units - 1] {
5503                    values.push(seconds * units + fraction);
5504                }
5505            }
5506        }
5507        for boundary in [1_000, 1_000_000] {
5508            values.extend(around(boundary));
5509        }
5510        let mut rng = StdRng::seed_from_u64(42);
5511        for _ in 0..256 {
5512            values.push(rng.random());
5513            let seconds = rng.random_range(-2_000_000_000..2_000_000_000);
5514            values.push(seconds * units + rng.random_range(0..units));
5515        }
5516        values.retain(|&v| as_datetime::<T>(v).is_some());
5517        let no_nulls = PrimitiveArray::<T>::new(values.clone().into(), None);
5518        let mixed = PrimitiveArray::<T>::from_iter(
5519            values
5520                .iter()
5521                .enumerate()
5522                .map(|(i, &v)| (i % 5 != 0).then_some(v)),
5523        );
5524        for array in [no_nulls, mixed.slice(1, mixed.len() - 2)] {
5525            let dates: Vec<_> = array
5526                .iter()
5527                .map(|v| v.map(|v| as_datetime::<T>(v).unwrap()))
5528                .collect();
5529            let expected: [ArrayRef; 5] = [
5530                Arc::new(Date32Array::from_iter(
5531                    dates
5532                        .iter()
5533                        .map(|d| d.map(|d| Date32Type::from_naive_date(d.date()))),
5534                )),
5535                Arc::new(Time32SecondArray::from_iter(
5536                    dates.iter().map(|d| d.map(|d| time_to_time32s(d.time()))),
5537                )),
5538                Arc::new(Time32MillisecondArray::from_iter(
5539                    dates.iter().map(|d| d.map(|d| time_to_time32ms(d.time()))),
5540                )),
5541                Arc::new(Time64MicrosecondArray::from_iter(
5542                    dates.iter().map(|d| d.map(|d| time_to_time64us(d.time()))),
5543                )),
5544                Arc::new(Time64NanosecondArray::from_iter(
5545                    dates.iter().map(|d| d.map(|d| time_to_time64ns(d.time()))),
5546                )),
5547            ];
5548            for expected in expected {
5549                let actual = cast(&array, expected.data_type()).unwrap();
5550                assert_eq!(actual.as_ref(), expected.as_ref(), "{}", T::DATA_TYPE);
5551            }
5552        }
5553    }
5554
5555    #[test]
5556    fn test_cast_timestamp_without_timezone_matches_chrono() {
5557        check_timestamp_casts::<TimestampSecondType>();
5558        check_timestamp_casts::<TimestampMillisecondType>();
5559        check_timestamp_casts::<TimestampMicrosecondType>();
5560        check_timestamp_casts::<TimestampNanosecondType>();
5561    }
5562
5563    #[test]
5564    fn test_cast_timestamp_to_time_extremes() {
5565        fn check<T: ArrowTimestampType>(min: (u32, u32, u32, u32), max: (u32, u32, u32, u32)) {
5566            let time = |(h, m, s, ns)| NaiveTime::from_hms_nano_opt(h, m, s, ns).unwrap();
5567            let times = [Some(time(min)), None, Some(time(max))];
5568            let array = PrimitiveArray::<T>::from_iter([Some(i64::MIN), None, Some(i64::MAX)]);
5569            let expected: [ArrayRef; 4] = [
5570                Arc::new(Time32SecondArray::from_iter(
5571                    times.map(|v| v.map(time_to_time32s)),
5572                )),
5573                Arc::new(Time32MillisecondArray::from_iter(
5574                    times.map(|v| v.map(time_to_time32ms)),
5575                )),
5576                Arc::new(Time64MicrosecondArray::from_iter(
5577                    times.map(|v| v.map(time_to_time64us)),
5578                )),
5579                Arc::new(Time64NanosecondArray::from_iter(
5580                    times.map(|v| v.map(time_to_time64ns)),
5581                )),
5582            ];
5583            for expected in expected {
5584                assert_eq!(
5585                    cast(&array, expected.data_type()).unwrap().as_ref(),
5586                    expected.as_ref()
5587                );
5588            }
5589        }
5590        check::<TimestampSecondType>((8, 29, 52, 0), (15, 30, 7, 0));
5591        check::<TimestampMillisecondType>((16, 47, 4, 192_000_000), (7, 12, 55, 807_000_000));
5592        check::<TimestampMicrosecondType>((19, 59, 5, 224_192_000), (4, 0, 54, 775_807_000));
5593        // Nanosecond extremes are representable in Chrono and covered above.
5594    }
5595
5596    #[test]
5597    fn test_cast_timestamp_to_date32_range() {
5598        fn check<T: ArrowTimestampType>() {
5599            let day = SECONDS_IN_DAY * time_unit_multiple(&T::UNIT);
5600            let first = i32::MIN as i64 * day;
5601            let last = (i32::MAX as i64 + 1) * day - 1;
5602            let array = PrimitiveArray::<T>::new(
5603                vec![first, i64::MAX, last].into(),
5604                Some(NullBuffer::from(vec![true, false, true])),
5605            );
5606            let expected = Date32Array::from(vec![Some(i32::MIN), None, Some(i32::MAX)]);
5607            for safe in [true, false] {
5608                let options = CastOptions {
5609                    safe,
5610                    ..Default::default()
5611                };
5612                assert_eq!(
5613                    cast_with_options(&array, &Date32, &options)
5614                        .unwrap()
5615                        .as_ref(),
5616                    &expected
5617                );
5618            }
5619            // Day counts that do not fit in i32 become null when safe, otherwise an error.
5620            let array = PrimitiveArray::<T>::from_iter_values([
5621                first - 1,
5622                last,
5623                last + 1,
5624                i64::MIN,
5625                i64::MAX,
5626            ]);
5627            let expected = Date32Array::from(vec![None, Some(i32::MAX), None, None, None]);
5628            assert_eq!(cast(&array, &Date32).unwrap().as_ref(), &expected);
5629            let options = CastOptions {
5630                safe: false,
5631                ..Default::default()
5632            };
5633            assert!(cast_with_options(&array, &Date32, &options).is_err());
5634        }
5635        check::<TimestampSecondType>();
5636        check::<TimestampMillisecondType>();
5637        // The entire microsecond domain fits in Date32, including dates outside Chrono's range.
5638        let array = TimestampMicrosecondArray::from(vec![Some(i64::MIN), None, Some(i64::MAX)]);
5639        assert_eq!(
5640            cast(&array, &Date32).unwrap().as_ref(),
5641            &Date32Array::from(vec![Some(-106_751_992), None, Some(106_751_991)]),
5642        );
5643    }
5644
5645    #[test]
5646    fn test_cast_timestamp_date_time_timezone_validation() {
5647        let invalid = TimestampSecondArray::from(vec![0]).with_timezone("invalid timezone");
5648        let extreme = TimestampSecondArray::from(vec![0, i64::MAX]).with_timezone("+00:00");
5649        let options = CastOptions {
5650            safe: false,
5651            ..Default::default()
5652        };
5653        for target in [
5654            Date32,
5655            Time32(TimeUnit::Second),
5656            Time32(TimeUnit::Millisecond),
5657            Time64(TimeUnit::Microsecond),
5658            Time64(TimeUnit::Nanosecond),
5659        ] {
5660            // A timezone that fails to parse is an error even when the cast is safe.
5661            assert!(cast(&invalid, &target).is_err());
5662            // A timestamp outside Chrono's date range is null when safe, otherwise an error.
5663            let actual = cast(&extreme, &target).unwrap();
5664            assert!(actual.is_valid(0));
5665            assert!(actual.is_null(1));
5666            assert!(cast_with_options(&extreme, &target, &options).is_err());
5667        }
5668    }
5669
5670    #[test]
5671    fn test_cast_timestamp_to_date32() {
5672        let array =
5673            TimestampMillisecondArray::from(vec![Some(864000000005), Some(1545696000001), None])
5674                .with_timezone("+00:00".to_string());
5675        let b = cast(&array, &DataType::Date32).unwrap();
5676        let c = b.as_primitive::<Date32Type>();
5677        assert_eq!(10000, c.value(0));
5678        assert_eq!(17890, c.value(1));
5679        assert!(c.is_null(2));
5680    }
5681    #[test]
5682    fn test_cast_timestamp_to_date32_zone() {
5683        let strings = StringArray::from_iter([
5684            Some("1970-01-01T00:00:01"),
5685            Some("1970-01-01T23:59:59"),
5686            None,
5687            Some("2020-03-01T02:00:23+00:00"),
5688        ]);
5689        let dt = DataType::Timestamp(TimeUnit::Millisecond, Some("-07:00".into()));
5690        let timestamps = cast(&strings, &dt).unwrap();
5691        let dates = cast(timestamps.as_ref(), &DataType::Date32).unwrap();
5692
5693        let c = dates.as_primitive::<Date32Type>();
5694        let expected = NaiveDate::from_ymd_opt(1970, 1, 1).unwrap();
5695        assert_eq!(c.value_as_date(0).unwrap(), expected);
5696        assert_eq!(c.value_as_date(1).unwrap(), expected);
5697        assert!(c.is_null(2));
5698        let expected = NaiveDate::from_ymd_opt(2020, 2, 29).unwrap();
5699        assert_eq!(c.value_as_date(3).unwrap(), expected);
5700    }
5701    #[test]
5702    fn test_cast_timestamp_to_date64() {
5703        let array =
5704            TimestampMillisecondArray::from(vec![Some(864000000005), Some(1545696000001), None]);
5705        let b = cast(&array, &DataType::Date64).unwrap();
5706        let c = b.as_primitive::<Date64Type>();
5707        assert_eq!(864000000000, c.value(0));
5708        assert_eq!(1545696000000, c.value(1));
5709        assert!(c.is_null(2));
5710
5711        let array = TimestampSecondArray::from(vec![Some(864000000005), Some(1545696000001)]);
5712        let b = cast(&array, &DataType::Date64).unwrap();
5713        let c = b.as_primitive::<Date64Type>();
5714        assert_eq!(864000000000000, c.value(0));
5715        assert_eq!(1545696000000000, c.value(1));
5716
5717        // test overflow, safe cast
5718        let array = TimestampSecondArray::from(vec![Some(i64::MAX)]);
5719        let b = cast(&array, &DataType::Date64).unwrap();
5720        assert!(b.is_null(0));
5721        // test overflow, unsafe cast
5722        let array = TimestampSecondArray::from(vec![Some(i64::MAX)]);
5723        let options = CastOptions {
5724            safe: false,
5725            format_options: FormatOptions::default(),
5726        };
5727        let b = cast_with_options(&array, &DataType::Date64, &options);
5728        assert!(b.is_err());
5729    }
5730
5731    #[test]
5732    fn test_cast_timestamp_to_date64_whole_days() {
5733        // 2024-05-01T10:30:00, 1970-01-01T00:00:00, and one millisecond before the epoch
5734        let millis: [i64; 3] = [1_714_559_400_000, 0, -1];
5735        let expected = Date64Array::from(vec![1_714_521_600_000, 0, -MILLISECONDS_IN_DAY]);
5736        let arrays: [ArrayRef; 4] = [
5737            Arc::new(TimestampSecondArray::from(
5738                millis.map(|x| x.div_euclid(1_000)).to_vec(),
5739            )),
5740            Arc::new(TimestampMillisecondArray::from(millis.to_vec())),
5741            Arc::new(TimestampMicrosecondArray::from(
5742                millis.map(|x| x * 1_000).to_vec(),
5743            )),
5744            Arc::new(TimestampNanosecondArray::from(
5745                millis.map(|x| x * 1_000_000).to_vec(),
5746            )),
5747        ];
5748        for array in arrays {
5749            let actual = cast(&array, &DataType::Date64).unwrap();
5750            let actual = actual.as_primitive::<Date64Type>();
5751            // The second timestamp array rounds -1ms down to -1s, which is still the
5752            // day before the epoch.
5753            assert_eq!(actual, &expected, "{}", array.data_type());
5754        }
5755
5756        // With a timezone the date is the local date, as for Date32.
5757        // 1970-01-01T00:00:01Z and 1970-01-01T20:00:00Z are 1969-12-31 and 1970-01-01 in -05:00.
5758        let array = TimestampSecondArray::from(vec![1, 72_000]).with_timezone("-05:00");
5759        let date64 = cast(&array, &DataType::Date64).unwrap();
5760        assert_eq!(
5761            date64.as_primitive::<Date64Type>(),
5762            &Date64Array::from(vec![-MILLISECONDS_IN_DAY, 0])
5763        );
5764        let date32 = cast(&array, &DataType::Date32).unwrap();
5765        assert_eq!(
5766            cast(&date32, &DataType::Date64).unwrap().as_ref(),
5767            date64.as_ref()
5768        );
5769
5770        // Flooring i64::MIN milliseconds to a whole day overflows.
5771        let array = TimestampMillisecondArray::from(vec![i64::MIN]);
5772        assert!(cast(&array, &DataType::Date64).unwrap().is_null(0));
5773        let options = CastOptions {
5774            safe: false,
5775            ..Default::default()
5776        };
5777        assert!(cast_with_options(&array, &DataType::Date64, &options).is_err());
5778    }
5779
5780    #[test]
5781    fn test_cast_timestamp_to_time64() {
5782        // test timestamp secs
5783        let array = TimestampSecondArray::from(vec![Some(86405), Some(1), None])
5784            .with_timezone("+01:00".to_string());
5785        let b = cast(&array, &DataType::Time64(TimeUnit::Microsecond)).unwrap();
5786        let c = b.as_primitive::<Time64MicrosecondType>();
5787        assert_eq!(3605000000, c.value(0));
5788        assert_eq!(3601000000, c.value(1));
5789        assert!(c.is_null(2));
5790        let b = cast(&array, &DataType::Time64(TimeUnit::Nanosecond)).unwrap();
5791        let c = b.as_primitive::<Time64NanosecondType>();
5792        assert_eq!(3605000000000, c.value(0));
5793        assert_eq!(3601000000000, c.value(1));
5794        assert!(c.is_null(2));
5795
5796        // test timestamp milliseconds
5797        let a = TimestampMillisecondArray::from(vec![Some(86405000), Some(1000), None])
5798            .with_timezone("+01:00".to_string());
5799        let array = Arc::new(a) as ArrayRef;
5800        let b = cast(&array, &DataType::Time64(TimeUnit::Microsecond)).unwrap();
5801        let c = b.as_primitive::<Time64MicrosecondType>();
5802        assert_eq!(3605000000, c.value(0));
5803        assert_eq!(3601000000, c.value(1));
5804        assert!(c.is_null(2));
5805        let b = cast(&array, &DataType::Time64(TimeUnit::Nanosecond)).unwrap();
5806        let c = b.as_primitive::<Time64NanosecondType>();
5807        assert_eq!(3605000000000, c.value(0));
5808        assert_eq!(3601000000000, c.value(1));
5809        assert!(c.is_null(2));
5810
5811        // test timestamp microseconds
5812        let a = TimestampMicrosecondArray::from(vec![Some(86405000000), Some(1000000), None])
5813            .with_timezone("+01:00".to_string());
5814        let array = Arc::new(a) as ArrayRef;
5815        let b = cast(&array, &DataType::Time64(TimeUnit::Microsecond)).unwrap();
5816        let c = b.as_primitive::<Time64MicrosecondType>();
5817        assert_eq!(3605000000, c.value(0));
5818        assert_eq!(3601000000, c.value(1));
5819        assert!(c.is_null(2));
5820        let b = cast(&array, &DataType::Time64(TimeUnit::Nanosecond)).unwrap();
5821        let c = b.as_primitive::<Time64NanosecondType>();
5822        assert_eq!(3605000000000, c.value(0));
5823        assert_eq!(3601000000000, c.value(1));
5824        assert!(c.is_null(2));
5825
5826        // Test fractional timestamps on both sides of the epoch.
5827        let a = TimestampNanosecondArray::from(vec![Some(86_405_123_456_789), Some(-1), None])
5828            .with_timezone("+01:00".to_string());
5829        let array = Arc::new(a) as ArrayRef;
5830        let b = cast(&array, &DataType::Time64(TimeUnit::Microsecond)).unwrap();
5831        let c = b.as_primitive::<Time64MicrosecondType>();
5832        assert_eq!(3_605_123_456, c.value(0));
5833        assert_eq!(3_599_999_999, c.value(1));
5834        assert!(c.is_null(2));
5835        let b = cast(&array, &DataType::Time64(TimeUnit::Nanosecond)).unwrap();
5836        let c = b.as_primitive::<Time64NanosecondType>();
5837        assert_eq!(3_605_123_456_789, c.value(0));
5838        assert_eq!(3_599_999_999_999, c.value(1));
5839        assert!(c.is_null(2));
5840
5841        // test overflow, safe cast
5842        let a =
5843            TimestampSecondArray::from(vec![Some(i64::MAX)]).with_timezone("+01:00".to_string());
5844        let array = Arc::new(a) as ArrayRef;
5845        let b = cast(&array, &DataType::Time64(TimeUnit::Microsecond)).unwrap();
5846        assert!(b.is_null(0));
5847        let b = cast(&array, &DataType::Time64(TimeUnit::Nanosecond)).unwrap();
5848        assert!(b.is_null(0));
5849        // test overflow, unsafe cast
5850        let options = CastOptions {
5851            safe: false,
5852            ..Default::default()
5853        };
5854        let b = cast_with_options(&array, &DataType::Time64(TimeUnit::Microsecond), &options);
5855        assert!(b.is_err());
5856        let b = cast_with_options(&array, &DataType::Time64(TimeUnit::Nanosecond), &options);
5857        assert!(b.is_err());
5858        // Time64 only supports microseconds and nanoseconds
5859        let b = cast(&array, &DataType::Time64(TimeUnit::Millisecond));
5860        assert!(b.is_err());
5861    }
5862
5863    #[test]
5864    fn test_cast_timestamp_to_time32() {
5865        // test timestamp secs
5866        let a = TimestampSecondArray::from(vec![Some(86405), Some(1), None])
5867            .with_timezone("+01:00".to_string());
5868        let array = Arc::new(a) as ArrayRef;
5869        let b = cast(&array, &DataType::Time32(TimeUnit::Second)).unwrap();
5870        let c = b.as_primitive::<Time32SecondType>();
5871        assert_eq!(3605, c.value(0));
5872        assert_eq!(3601, c.value(1));
5873        assert!(c.is_null(2));
5874        let b = cast(&array, &DataType::Time32(TimeUnit::Millisecond)).unwrap();
5875        let c = b.as_primitive::<Time32MillisecondType>();
5876        assert_eq!(3605000, c.value(0));
5877        assert_eq!(3601000, c.value(1));
5878        assert!(c.is_null(2));
5879
5880        // test timestamp milliseconds
5881        let a = TimestampMillisecondArray::from(vec![Some(86405000), Some(1000), None])
5882            .with_timezone("+01:00".to_string());
5883        let array = Arc::new(a) as ArrayRef;
5884        let b = cast(&array, &DataType::Time32(TimeUnit::Second)).unwrap();
5885        let c = b.as_primitive::<Time32SecondType>();
5886        assert_eq!(3605, c.value(0));
5887        assert_eq!(3601, c.value(1));
5888        assert!(c.is_null(2));
5889        let b = cast(&array, &DataType::Time32(TimeUnit::Millisecond)).unwrap();
5890        let c = b.as_primitive::<Time32MillisecondType>();
5891        assert_eq!(3605000, c.value(0));
5892        assert_eq!(3601000, c.value(1));
5893        assert!(c.is_null(2));
5894
5895        // test timestamp microseconds
5896        let a = TimestampMicrosecondArray::from(vec![Some(86405000000), Some(1000000), None])
5897            .with_timezone("+01:00".to_string());
5898        let array = Arc::new(a) as ArrayRef;
5899        let b = cast(&array, &DataType::Time32(TimeUnit::Second)).unwrap();
5900        let c = b.as_primitive::<Time32SecondType>();
5901        assert_eq!(3605, c.value(0));
5902        assert_eq!(3601, c.value(1));
5903        assert!(c.is_null(2));
5904        let b = cast(&array, &DataType::Time32(TimeUnit::Millisecond)).unwrap();
5905        let c = b.as_primitive::<Time32MillisecondType>();
5906        assert_eq!(3605000, c.value(0));
5907        assert_eq!(3601000, c.value(1));
5908        assert!(c.is_null(2));
5909
5910        // Test fractional timestamps on both sides of the epoch.
5911        let a = TimestampNanosecondArray::from(vec![Some(86_405_123_456_789), Some(-1), None])
5912            .with_timezone("+01:00".to_string());
5913        let array = Arc::new(a) as ArrayRef;
5914        let b = cast(&array, &DataType::Time32(TimeUnit::Second)).unwrap();
5915        let c = b.as_primitive::<Time32SecondType>();
5916        assert_eq!(3605, c.value(0));
5917        assert_eq!(3599, c.value(1));
5918        assert!(c.is_null(2));
5919        let b = cast(&array, &DataType::Time32(TimeUnit::Millisecond)).unwrap();
5920        let c = b.as_primitive::<Time32MillisecondType>();
5921        assert_eq!(3_605_123, c.value(0));
5922        assert_eq!(3_599_999, c.value(1));
5923        assert!(c.is_null(2));
5924
5925        // test overflow, safe cast
5926        let a =
5927            TimestampSecondArray::from(vec![Some(i64::MAX)]).with_timezone("+01:00".to_string());
5928        let array = Arc::new(a) as ArrayRef;
5929        let b = cast(&array, &DataType::Time32(TimeUnit::Second)).unwrap();
5930        assert!(b.is_null(0));
5931        let b = cast(&array, &DataType::Time32(TimeUnit::Millisecond)).unwrap();
5932        assert!(b.is_null(0));
5933        // test overflow, unsafe cast
5934        let options = CastOptions {
5935            safe: false,
5936            ..Default::default()
5937        };
5938        let b = cast_with_options(&array, &DataType::Time32(TimeUnit::Second), &options);
5939        assert!(b.is_err());
5940        let b = cast_with_options(&array, &DataType::Time32(TimeUnit::Millisecond), &options);
5941        assert!(b.is_err());
5942    }
5943
5944    // Cast Timestamp(_, None) -> Timestamp(_, Some(timezone))
5945    #[test]
5946    fn test_cast_timestamp_with_timezone_1() {
5947        let string_array: Arc<dyn Array> = Arc::new(StringArray::from(vec![
5948            Some("2000-01-01T00:00:00.123456789"),
5949            Some("2010-01-01T00:00:00.123456789"),
5950            None,
5951        ]));
5952        let to_type = DataType::Timestamp(TimeUnit::Nanosecond, None);
5953        let timestamp_array = cast(&string_array, &to_type).unwrap();
5954
5955        let to_type = DataType::Timestamp(TimeUnit::Microsecond, Some("+0700".into()));
5956        let timestamp_array = cast(&timestamp_array, &to_type).unwrap();
5957
5958        let string_array = cast(&timestamp_array, &DataType::Utf8).unwrap();
5959        let result = string_array.as_string::<i32>();
5960        assert_eq!("2000-01-01T00:00:00.123456+07:00", result.value(0));
5961        assert_eq!("2010-01-01T00:00:00.123456+07:00", result.value(1));
5962        assert!(result.is_null(2));
5963    }
5964
5965    // Cast Timestamp(_, Some(timezone)) -> Timestamp(_, None)
5966    #[test]
5967    fn test_cast_timestamp_with_timezone_2() {
5968        let string_array: Arc<dyn Array> = Arc::new(StringArray::from(vec![
5969            Some("2000-01-01T07:00:00.123456789"),
5970            Some("2010-01-01T07:00:00.123456789"),
5971            None,
5972        ]));
5973        let to_type = DataType::Timestamp(TimeUnit::Millisecond, Some("+0700".into()));
5974        let timestamp_array = cast(&string_array, &to_type).unwrap();
5975
5976        // Check intermediate representation is correct
5977        let string_array = cast(&timestamp_array, &DataType::Utf8).unwrap();
5978        let result = string_array.as_string::<i32>();
5979        assert_eq!("2000-01-01T07:00:00.123+07:00", result.value(0));
5980        assert_eq!("2010-01-01T07:00:00.123+07:00", result.value(1));
5981        assert!(result.is_null(2));
5982
5983        let to_type = DataType::Timestamp(TimeUnit::Nanosecond, None);
5984        let timestamp_array = cast(&timestamp_array, &to_type).unwrap();
5985
5986        let string_array = cast(&timestamp_array, &DataType::Utf8).unwrap();
5987        let result = string_array.as_string::<i32>();
5988        assert_eq!("2000-01-01T00:00:00.123", result.value(0));
5989        assert_eq!("2010-01-01T00:00:00.123", result.value(1));
5990        assert!(result.is_null(2));
5991    }
5992
5993    // Cast Timestamp(_, Some(timezone)) -> Timestamp(_, Some(timezone))
5994    #[test]
5995    fn test_cast_timestamp_with_timezone_3() {
5996        let string_array: Arc<dyn Array> = Arc::new(StringArray::from(vec![
5997            Some("2000-01-01T07:00:00.123456789"),
5998            Some("2010-01-01T07:00:00.123456789"),
5999            None,
6000        ]));
6001        let to_type = DataType::Timestamp(TimeUnit::Microsecond, Some("+0700".into()));
6002        let timestamp_array = cast(&string_array, &to_type).unwrap();
6003
6004        // Check intermediate representation is correct
6005        let string_array = cast(&timestamp_array, &DataType::Utf8).unwrap();
6006        let result = string_array.as_string::<i32>();
6007        assert_eq!("2000-01-01T07:00:00.123456+07:00", result.value(0));
6008        assert_eq!("2010-01-01T07:00:00.123456+07:00", result.value(1));
6009        assert!(result.is_null(2));
6010
6011        let to_type = DataType::Timestamp(TimeUnit::Second, Some("-08:00".into()));
6012        let timestamp_array = cast(&timestamp_array, &to_type).unwrap();
6013
6014        let string_array = cast(&timestamp_array, &DataType::Utf8).unwrap();
6015        let result = string_array.as_string::<i32>();
6016        assert_eq!("1999-12-31T16:00:00-08:00", result.value(0));
6017        assert_eq!("2009-12-31T16:00:00-08:00", result.value(1));
6018        assert!(result.is_null(2));
6019    }
6020
6021    /// The i64 value of a `Timestamp(Second, None)` holding the given wall clock
6022    /// reading (a naive timestamp is stored as if it were UTC).
6023    fn naive_seconds(y: i32, m: u32, d: u32, h: u32, min: u32) -> i64 {
6024        NaiveDate::from_ymd_opt(y, m, d)
6025            .unwrap()
6026            .and_hms_opt(h, min, 0)
6027            .unwrap()
6028            .and_utc()
6029            .timestamp()
6030    }
6031
6032    /// The instant, in seconds since the epoch, denoted by the given wall clock
6033    /// reading at a fixed offset of `offset_hours`.
6034    fn instant_seconds(y: i32, m: u32, d: u32, h: u32, min: u32, offset_hours: i32) -> i64 {
6035        let offset = FixedOffset::east_opt(offset_hours * 3600).unwrap();
6036        NaiveDate::from_ymd_opt(y, m, d)
6037            .unwrap()
6038            .and_hms_opt(h, min, 0)
6039            .unwrap()
6040            .and_local_timezone(offset)
6041            .unwrap()
6042            .timestamp()
6043    }
6044
6045    // Cast Timestamp(_, None) -> Timestamp(_, Some(IANA timezone)) across DST
6046    // transitions. See `resolve_local_offset`.
6047    #[test]
6048    fn test_cast_timestamp_to_named_timezone_dst() {
6049        // Unambiguous, EDT (-04:00) is in effect.
6050        let unambiguous = naive_seconds(2024, 11, 1, 0, 0);
6051        // Ambiguous: the clocks go back at 2024-11-03T02:00 EDT, so 01:30
6052        // happens twice, first at -04:00 and then at -05:00.
6053        let ambiguous = naive_seconds(2024, 11, 3, 1, 30);
6054        // Nonexistent: the clocks go forward at 2024-03-10T02:00 EST, so 02:30
6055        // never happens.
6056        let nonexistent = naive_seconds(2024, 3, 10, 2, 30);
6057        assert_eq!(
6058            [unambiguous, ambiguous, nonexistent],
6059            [1_730_419_200, 1_730_597_400, 1_710_037_800]
6060        );
6061
6062        let array = TimestampSecondArray::from(vec![
6063            Some(unambiguous),
6064            Some(ambiguous),
6065            Some(nonexistent),
6066            None,
6067        ]);
6068        let to_type = DataType::Timestamp(TimeUnit::Second, Some("America/New_York".into()));
6069        let options = CastOptions {
6070            safe: false,
6071            ..Default::default()
6072        };
6073
6074        let b = cast_with_options(&array, &to_type, &options).unwrap();
6075        assert_eq!(b.data_type(), &to_type);
6076        let c = b.as_primitive::<TimestampSecondType>();
6077
6078        assert_eq!(c.value(0), instant_seconds(2024, 11, 1, 0, 0, -4));
6079        assert_eq!(c.value(0), 1_730_433_600);
6080        // The later of the two candidates, i.e. EST rather than EDT.
6081        assert_eq!(c.value(1), instant_seconds(2024, 11, 3, 1, 30, -5));
6082        assert_eq!(c.value(1), 1_730_615_400);
6083        // Shifted forward by the one hour gap: 02:30 EST is 03:30 EDT.
6084        assert_eq!(c.value(2), instant_seconds(2024, 3, 10, 2, 30, -5));
6085        assert_eq!(c.value(2), instant_seconds(2024, 3, 10, 3, 30, -4));
6086        assert_eq!(c.value(2), 1_710_055_800);
6087        assert!(c.is_null(3));
6088    }
6089
6090    // The same values must not become null when `safe` casting is requested.
6091    #[test]
6092    fn test_cast_timestamp_to_named_timezone_dst_safe() {
6093        let array = TimestampSecondArray::from(vec![
6094            Some(naive_seconds(2024, 11, 1, 0, 0)),
6095            Some(naive_seconds(2024, 11, 3, 1, 30)),
6096            Some(naive_seconds(2024, 3, 10, 2, 30)),
6097            None,
6098        ]);
6099        let to_type = DataType::Timestamp(TimeUnit::Second, Some("America/New_York".into()));
6100        let options = CastOptions {
6101            safe: true,
6102            ..Default::default()
6103        };
6104
6105        let b = cast_with_options(&array, &to_type, &options).unwrap();
6106        assert_eq!(b.data_type(), &to_type);
6107        let c = b.as_primitive::<TimestampSecondType>();
6108        assert_eq!(c.null_count(), 1);
6109        assert_eq!(c.value(0), 1_730_433_600);
6110        assert_eq!(c.value(1), 1_730_615_400);
6111        assert_eq!(c.value(2), 1_710_055_800);
6112        assert!(c.is_null(3));
6113    }
6114
6115    // Southern hemisphere: the transitions run the other way around.
6116    #[test]
6117    fn test_cast_timestamp_to_named_timezone_dst_southern_hemisphere() {
6118        // Ambiguous: clocks go back at 2024-04-07T03:00 AEDT (+11:00 -> +10:00).
6119        let ambiguous = naive_seconds(2024, 4, 7, 2, 30);
6120        // Nonexistent: clocks go forward at 2024-10-06T02:00 AEST (+10:00 -> +11:00).
6121        let nonexistent = naive_seconds(2024, 10, 6, 2, 30);
6122
6123        let array = TimestampSecondArray::from(vec![Some(ambiguous), Some(nonexistent)]);
6124        let to_type = DataType::Timestamp(TimeUnit::Second, Some("Australia/Sydney".into()));
6125        let options = CastOptions {
6126            safe: false,
6127            ..Default::default()
6128        };
6129
6130        let b = cast_with_options(&array, &to_type, &options).unwrap();
6131        assert_eq!(b.data_type(), &to_type);
6132        let c = b.as_primitive::<TimestampSecondType>();
6133
6134        // The later of the two candidates, i.e. AEST (+10:00).
6135        assert_eq!(c.value(0), instant_seconds(2024, 4, 7, 2, 30, 10));
6136        assert_eq!(c.value(0), 1_712_421_000);
6137        // Shifted forward by the one hour gap: 02:30 AEST is 03:30 AEDT.
6138        assert_eq!(c.value(1), instant_seconds(2024, 10, 6, 2, 30, 10));
6139        assert_eq!(c.value(1), instant_seconds(2024, 10, 6, 3, 30, 11));
6140        assert_eq!(c.value(1), 1_728_145_800);
6141    }
6142
6143    // The resolution is independent of the time unit.
6144    #[test]
6145    fn test_cast_timestamp_to_named_timezone_dst_nanosecond() {
6146        let ambiguous = naive_seconds(2024, 11, 3, 1, 30) * 1_000_000_000 + 123_456_789;
6147        let nonexistent = naive_seconds(2024, 3, 10, 2, 30) * 1_000_000_000 + 123_456_789;
6148        let array = TimestampNanosecondArray::from(vec![Some(ambiguous), Some(nonexistent)]);
6149        let to_type = DataType::Timestamp(TimeUnit::Nanosecond, Some("America/New_York".into()));
6150        let options = CastOptions {
6151            safe: false,
6152            ..Default::default()
6153        };
6154
6155        let b = cast_with_options(&array, &to_type, &options).unwrap();
6156        assert_eq!(b.data_type(), &to_type);
6157        let c = b.as_primitive::<TimestampNanosecondType>();
6158        assert_eq!(c.value(0), 1_730_615_400 * 1_000_000_000 + 123_456_789);
6159        assert_eq!(c.value(1), 1_710_055_800 * 1_000_000_000 + 123_456_789);
6160    }
6161
6162    // Unit conversion still composes with the timezone adjustment.
6163    #[test]
6164    fn test_cast_timestamp_to_named_timezone_dst_changing_unit() {
6165        let array = TimestampSecondArray::from(vec![
6166            Some(naive_seconds(2024, 11, 3, 1, 30)),
6167            Some(naive_seconds(2024, 3, 10, 2, 30)),
6168        ]);
6169        let to_type = DataType::Timestamp(TimeUnit::Millisecond, Some("America/New_York".into()));
6170        let options = CastOptions {
6171            safe: false,
6172            ..Default::default()
6173        };
6174
6175        let b = cast_with_options(&array, &to_type, &options).unwrap();
6176        assert_eq!(b.data_type(), &to_type);
6177        let c = b.as_primitive::<TimestampMillisecondType>();
6178        assert_eq!(c.value(0), 1_730_615_400_000);
6179        assert_eq!(c.value(1), 1_710_055_800_000);
6180    }
6181
6182    // A fixed offset has no transitions, so the same readings are unaffected.
6183    #[test]
6184    fn test_cast_timestamp_to_fixed_offset_timezone_unaffected() {
6185        let array = TimestampSecondArray::from(vec![
6186            Some(naive_seconds(2024, 11, 1, 0, 0)),
6187            Some(naive_seconds(2024, 11, 3, 1, 30)),
6188            Some(naive_seconds(2024, 3, 10, 2, 30)),
6189            None,
6190        ]);
6191        let to_type = DataType::Timestamp(TimeUnit::Second, Some("+08:00".into()));
6192        let options = CastOptions {
6193            safe: false,
6194            ..Default::default()
6195        };
6196
6197        let b = cast_with_options(&array, &to_type, &options).unwrap();
6198        assert_eq!(b.data_type(), &to_type);
6199        let c = b.as_primitive::<TimestampSecondType>();
6200        assert_eq!(c.value(0), instant_seconds(2024, 11, 1, 0, 0, 8));
6201        assert_eq!(c.value(1), instant_seconds(2024, 11, 3, 1, 30, 8));
6202        assert_eq!(c.value(2), instant_seconds(2024, 3, 10, 2, 30, 8));
6203        assert!(c.is_null(3));
6204    }
6205
6206    #[test]
6207    fn test_cast_date64_to_timestamp() {
6208        let array = Date64Array::from(vec![Some(864000000005), Some(1545696000001), None]);
6209        let b = cast(&array, &DataType::Timestamp(TimeUnit::Second, None)).unwrap();
6210        let c = b.as_primitive::<TimestampSecondType>();
6211        assert_eq!(864000000, c.value(0));
6212        assert_eq!(1545696000, c.value(1));
6213        assert!(c.is_null(2));
6214    }
6215
6216    #[test]
6217    fn test_cast_date64_to_timestamp_ms() {
6218        let array = Date64Array::from(vec![Some(864000000005), Some(1545696000001), None]);
6219        let b = cast(&array, &DataType::Timestamp(TimeUnit::Millisecond, None)).unwrap();
6220        let c = b
6221            .as_any()
6222            .downcast_ref::<TimestampMillisecondArray>()
6223            .unwrap();
6224        assert_eq!(864000000005, c.value(0));
6225        assert_eq!(1545696000001, c.value(1));
6226        assert!(c.is_null(2));
6227    }
6228
6229    #[test]
6230    fn test_cast_date64_to_timestamp_us() {
6231        let array = Date64Array::from(vec![Some(864000000005), Some(1545696000001), None]);
6232        let b = cast(&array, &DataType::Timestamp(TimeUnit::Microsecond, None)).unwrap();
6233        let c = b
6234            .as_any()
6235            .downcast_ref::<TimestampMicrosecondArray>()
6236            .unwrap();
6237        assert_eq!(864000000005000, c.value(0));
6238        assert_eq!(1545696000001000, c.value(1));
6239        assert!(c.is_null(2));
6240    }
6241
6242    #[test]
6243    fn test_cast_date64_to_timestamp_ns() {
6244        let array = Date64Array::from(vec![Some(864000000005), Some(1545696000001), None]);
6245        let b = cast(&array, &DataType::Timestamp(TimeUnit::Nanosecond, None)).unwrap();
6246        let c = b
6247            .as_any()
6248            .downcast_ref::<TimestampNanosecondArray>()
6249            .unwrap();
6250        assert_eq!(864000000005000000, c.value(0));
6251        assert_eq!(1545696000001000000, c.value(1));
6252        assert!(c.is_null(2));
6253    }
6254
6255    #[test]
6256    fn test_cast_timestamp_to_i64() {
6257        let array =
6258            TimestampMillisecondArray::from(vec![Some(864000000005), Some(1545696000001), None])
6259                .with_timezone("UTC".to_string());
6260        let b = cast(&array, &DataType::Int64).unwrap();
6261        let c = b.as_primitive::<Int64Type>();
6262        assert_eq!(&DataType::Int64, c.data_type());
6263        assert_eq!(864000000005, c.value(0));
6264        assert_eq!(1545696000001, c.value(1));
6265        assert!(c.is_null(2));
6266    }
6267
6268    macro_rules! assert_cast {
6269        ($array:expr, $datatype:expr, $output_array_type: ty, $expected:expr) => {{
6270            assert!(can_cast_types($array.data_type(), &$datatype));
6271            let out = cast(&$array, &$datatype).unwrap();
6272            let actual = out
6273                .as_any()
6274                .downcast_ref::<$output_array_type>()
6275                .unwrap()
6276                .into_iter()
6277                .collect::<Vec<_>>();
6278            assert_eq!(actual, $expected);
6279        }};
6280        ($array:expr, $datatype:expr, $output_array_type: ty, $options:expr, $expected:expr) => {{
6281            assert!(can_cast_types($array.data_type(), &$datatype));
6282            let out = cast_with_options(&$array, &$datatype, &$options).unwrap();
6283            let actual = out
6284                .as_any()
6285                .downcast_ref::<$output_array_type>()
6286                .unwrap()
6287                .into_iter()
6288                .collect::<Vec<_>>();
6289            assert_eq!(actual, $expected);
6290        }};
6291    }
6292
6293    #[test]
6294    fn test_cast_date32_to_string() {
6295        let array = Date32Array::from(vec![Some(0), Some(10000), Some(13036), Some(17890), None]);
6296        let expected = vec![
6297            Some("1970-01-01"),
6298            Some("1997-05-19"),
6299            Some("2005-09-10"),
6300            Some("2018-12-25"),
6301            None,
6302        ];
6303
6304        assert_cast!(array, DataType::Utf8View, StringViewArray, expected);
6305        assert_cast!(array, DataType::Utf8, StringArray, expected);
6306        assert_cast!(array, DataType::LargeUtf8, LargeStringArray, expected);
6307    }
6308
6309    #[test]
6310    fn test_cast_date64_to_string() {
6311        let array = Date64Array::from(vec![
6312            Some(0),
6313            Some(10000 * 86400000),
6314            Some(13036 * 86400000),
6315            Some(17890 * 86400000),
6316            None,
6317        ]);
6318        let expected = vec![
6319            Some("1970-01-01T00:00:00"),
6320            Some("1997-05-19T00:00:00"),
6321            Some("2005-09-10T00:00:00"),
6322            Some("2018-12-25T00:00:00"),
6323            None,
6324        ];
6325
6326        assert_cast!(array, DataType::Utf8View, StringViewArray, expected);
6327        assert_cast!(array, DataType::Utf8, StringArray, expected);
6328        assert_cast!(array, DataType::LargeUtf8, LargeStringArray, expected);
6329    }
6330
6331    #[test]
6332    fn test_cast_date32_to_timestamp_and_timestamp_with_timezone() {
6333        let tz = "+0545"; // UTC + 0545 is Asia/Kathmandu
6334        let a = Date32Array::from(vec![Some(18628), None, None]); // 2021-1-1, 2022-1-1
6335        let array = Arc::new(a) as ArrayRef;
6336
6337        let b = cast(
6338            &array,
6339            &DataType::Timestamp(TimeUnit::Second, Some(tz.into())),
6340        )
6341        .unwrap();
6342        let c = b.as_primitive::<TimestampSecondType>();
6343        let string_array = cast(&c, &DataType::Utf8).unwrap();
6344        let result = string_array.as_string::<i32>();
6345        assert_eq!("2021-01-01T00:00:00+05:45", result.value(0));
6346
6347        let b = cast(&array, &DataType::Timestamp(TimeUnit::Second, None)).unwrap();
6348        let c = b.as_primitive::<TimestampSecondType>();
6349        let string_array = cast(&c, &DataType::Utf8).unwrap();
6350        let result = string_array.as_string::<i32>();
6351        assert_eq!("2021-01-01T00:00:00", result.value(0));
6352    }
6353
6354    #[test]
6355    fn test_cast_date32_to_timestamp_with_timezone() {
6356        let tz = "+0545"; // UTC + 0545 is Asia/Kathmandu
6357        let a = Date32Array::from(vec![Some(18628), Some(18993), None]); // 2021-1-1, 2022-1-1
6358        let array = Arc::new(a) as ArrayRef;
6359        let b = cast(
6360            &array,
6361            &DataType::Timestamp(TimeUnit::Second, Some(tz.into())),
6362        )
6363        .unwrap();
6364        let c = b.as_primitive::<TimestampSecondType>();
6365        assert_eq!(1609438500, c.value(0));
6366        assert_eq!(1640974500, c.value(1));
6367        assert!(c.is_null(2));
6368
6369        let string_array = cast(&c, &DataType::Utf8).unwrap();
6370        let result = string_array.as_string::<i32>();
6371        assert_eq!("2021-01-01T00:00:00+05:45", result.value(0));
6372        assert_eq!("2022-01-01T00:00:00+05:45", result.value(1));
6373    }
6374
6375    #[test]
6376    fn test_cast_date32_to_timestamp_with_timezone_ms() {
6377        let tz = "+0545"; // UTC + 0545 is Asia/Kathmandu
6378        let a = Date32Array::from(vec![Some(18628), Some(18993), None]); // 2021-1-1, 2022-1-1
6379        let array = Arc::new(a) as ArrayRef;
6380        let b = cast(
6381            &array,
6382            &DataType::Timestamp(TimeUnit::Millisecond, Some(tz.into())),
6383        )
6384        .unwrap();
6385        let c = b.as_primitive::<TimestampMillisecondType>();
6386        assert_eq!(1609438500000, c.value(0));
6387        assert_eq!(1640974500000, c.value(1));
6388        assert!(c.is_null(2));
6389
6390        let string_array = cast(&c, &DataType::Utf8).unwrap();
6391        let result = string_array.as_string::<i32>();
6392        assert_eq!("2021-01-01T00:00:00+05:45", result.value(0));
6393        assert_eq!("2022-01-01T00:00:00+05:45", result.value(1));
6394    }
6395
6396    #[test]
6397    fn test_cast_date32_to_timestamp_with_timezone_us() {
6398        let tz = "+0545"; // UTC + 0545 is Asia/Kathmandu
6399        let a = Date32Array::from(vec![Some(18628), Some(18993), None]); // 2021-1-1, 2022-1-1
6400        let array = Arc::new(a) as ArrayRef;
6401        let b = cast(
6402            &array,
6403            &DataType::Timestamp(TimeUnit::Microsecond, Some(tz.into())),
6404        )
6405        .unwrap();
6406        let c = b.as_primitive::<TimestampMicrosecondType>();
6407        assert_eq!(1609438500000000, c.value(0));
6408        assert_eq!(1640974500000000, c.value(1));
6409        assert!(c.is_null(2));
6410
6411        let string_array = cast(&c, &DataType::Utf8).unwrap();
6412        let result = string_array.as_string::<i32>();
6413        assert_eq!("2021-01-01T00:00:00+05:45", result.value(0));
6414        assert_eq!("2022-01-01T00:00:00+05:45", result.value(1));
6415    }
6416
6417    #[test]
6418    fn test_cast_date32_to_timestamp_with_timezone_ns() {
6419        let tz = "+0545"; // UTC + 0545 is Asia/Kathmandu
6420        let a = Date32Array::from(vec![Some(18628), Some(18993), None]); // 2021-1-1, 2022-1-1
6421        let array = Arc::new(a) as ArrayRef;
6422        let b = cast(
6423            &array,
6424            &DataType::Timestamp(TimeUnit::Nanosecond, Some(tz.into())),
6425        )
6426        .unwrap();
6427        let c = b.as_primitive::<TimestampNanosecondType>();
6428        assert_eq!(1609438500000000000, c.value(0));
6429        assert_eq!(1640974500000000000, c.value(1));
6430        assert!(c.is_null(2));
6431
6432        let string_array = cast(&c, &DataType::Utf8).unwrap();
6433        let result = string_array.as_string::<i32>();
6434        assert_eq!("2021-01-01T00:00:00+05:45", result.value(0));
6435        assert_eq!("2022-01-01T00:00:00+05:45", result.value(1));
6436    }
6437
6438    #[test]
6439    fn test_cast_date64_to_timestamp_with_timezone() {
6440        let array = Date64Array::from(vec![Some(864000000005), Some(1545696000001), None]);
6441        let tz = "+0545"; // UTC + 0545 is Asia/Kathmandu
6442        let b = cast(
6443            &array,
6444            &DataType::Timestamp(TimeUnit::Second, Some(tz.into())),
6445        )
6446        .unwrap();
6447
6448        let c = b.as_primitive::<TimestampSecondType>();
6449        assert_eq!(863979300, c.value(0));
6450        assert_eq!(1545675300, c.value(1));
6451        assert!(c.is_null(2));
6452
6453        let string_array = cast(&c, &DataType::Utf8).unwrap();
6454        let result = string_array.as_string::<i32>();
6455        assert_eq!("1997-05-19T00:00:00+05:45", result.value(0));
6456        assert_eq!("2018-12-25T00:00:00+05:45", result.value(1));
6457    }
6458
6459    #[test]
6460    fn test_cast_date64_to_timestamp_with_timezone_ms() {
6461        let array = Date64Array::from(vec![Some(864000000005), Some(1545696000001), None]);
6462        let tz = "+0545"; // UTC + 0545 is Asia/Kathmandu
6463        let b = cast(
6464            &array,
6465            &DataType::Timestamp(TimeUnit::Millisecond, Some(tz.into())),
6466        )
6467        .unwrap();
6468
6469        let c = b.as_primitive::<TimestampMillisecondType>();
6470        assert_eq!(863979300005, c.value(0));
6471        assert_eq!(1545675300001, c.value(1));
6472        assert!(c.is_null(2));
6473
6474        let string_array = cast(&c, &DataType::Utf8).unwrap();
6475        let result = string_array.as_string::<i32>();
6476        assert_eq!("1997-05-19T00:00:00.005+05:45", result.value(0));
6477        assert_eq!("2018-12-25T00:00:00.001+05:45", result.value(1));
6478    }
6479
6480    #[test]
6481    fn test_cast_date64_to_timestamp_with_timezone_us() {
6482        let array = Date64Array::from(vec![Some(864000000005), Some(1545696000001), None]);
6483        let tz = "+0545"; // UTC + 0545 is Asia/Kathmandu
6484        let b = cast(
6485            &array,
6486            &DataType::Timestamp(TimeUnit::Microsecond, Some(tz.into())),
6487        )
6488        .unwrap();
6489
6490        let c = b.as_primitive::<TimestampMicrosecondType>();
6491        assert_eq!(863979300005000, c.value(0));
6492        assert_eq!(1545675300001000, c.value(1));
6493        assert!(c.is_null(2));
6494
6495        let string_array = cast(&c, &DataType::Utf8).unwrap();
6496        let result = string_array.as_string::<i32>();
6497        assert_eq!("1997-05-19T00:00:00.005+05:45", result.value(0));
6498        assert_eq!("2018-12-25T00:00:00.001+05:45", result.value(1));
6499    }
6500
6501    #[test]
6502    fn test_cast_date64_to_timestamp_with_timezone_ns() {
6503        let array = Date64Array::from(vec![Some(864000000005), Some(1545696000001), None]);
6504        let tz = "+0545"; // UTC + 0545 is Asia/Kathmandu
6505        let b = cast(
6506            &array,
6507            &DataType::Timestamp(TimeUnit::Nanosecond, Some(tz.into())),
6508        )
6509        .unwrap();
6510
6511        let c = b.as_primitive::<TimestampNanosecondType>();
6512        assert_eq!(863979300005000000, c.value(0));
6513        assert_eq!(1545675300001000000, c.value(1));
6514        assert!(c.is_null(2));
6515
6516        let string_array = cast(&c, &DataType::Utf8).unwrap();
6517        let result = string_array.as_string::<i32>();
6518        assert_eq!("1997-05-19T00:00:00.005+05:45", result.value(0));
6519        assert_eq!("2018-12-25T00:00:00.001+05:45", result.value(1));
6520    }
6521
6522    #[test]
6523    fn test_cast_timestamp_to_strings() {
6524        // "2018-12-25T00:00:02.001", "1997-05-19T00:00:03.005", None
6525        let array =
6526            TimestampMillisecondArray::from(vec![Some(864000003005), Some(1545696002001), None]);
6527        let expected = vec![
6528            Some("1997-05-19T00:00:03.005"),
6529            Some("2018-12-25T00:00:02.001"),
6530            None,
6531        ];
6532
6533        assert_cast!(array, DataType::Utf8View, StringViewArray, expected);
6534        assert_cast!(array, DataType::Utf8, StringArray, expected);
6535        assert_cast!(array, DataType::LargeUtf8, LargeStringArray, expected);
6536    }
6537
6538    #[test]
6539    fn test_cast_timestamp_to_strings_opt() {
6540        let ts_format = "%Y-%m-%d %H:%M:%S%.6f";
6541        let tz = "+0545"; // UTC + 0545 is Asia/Kathmandu
6542        let cast_options = CastOptions {
6543            safe: true,
6544            format_options: FormatOptions::default()
6545                .with_timestamp_format(Some(ts_format))
6546                .with_timestamp_tz_format(Some(ts_format)),
6547        };
6548
6549        // "2018-12-25T00:00:02.001", "1997-05-19T00:00:03.005", None
6550        let array_without_tz =
6551            TimestampMillisecondArray::from(vec![Some(864000003005), Some(1545696002001), None]);
6552        let expected = vec![
6553            Some("1997-05-19 00:00:03.005000"),
6554            Some("2018-12-25 00:00:02.001000"),
6555            None,
6556        ];
6557        assert_cast!(
6558            array_without_tz,
6559            DataType::Utf8View,
6560            StringViewArray,
6561            cast_options,
6562            expected
6563        );
6564        assert_cast!(
6565            array_without_tz,
6566            DataType::Utf8,
6567            StringArray,
6568            cast_options,
6569            expected
6570        );
6571        assert_cast!(
6572            array_without_tz,
6573            DataType::LargeUtf8,
6574            LargeStringArray,
6575            cast_options,
6576            expected
6577        );
6578
6579        let array_with_tz =
6580            TimestampMillisecondArray::from(vec![Some(864000003005), Some(1545696002001), None])
6581                .with_timezone(tz.to_string());
6582        let expected = vec![
6583            Some("1997-05-19 05:45:03.005000"),
6584            Some("2018-12-25 05:45:02.001000"),
6585            None,
6586        ];
6587        assert_cast!(
6588            array_with_tz,
6589            DataType::Utf8View,
6590            StringViewArray,
6591            cast_options,
6592            expected
6593        );
6594        assert_cast!(
6595            array_with_tz,
6596            DataType::Utf8,
6597            StringArray,
6598            cast_options,
6599            expected
6600        );
6601        assert_cast!(
6602            array_with_tz,
6603            DataType::LargeUtf8,
6604            LargeStringArray,
6605            cast_options,
6606            expected
6607        );
6608    }
6609
6610    #[test]
6611    fn test_cast_between_timestamps() {
6612        let array =
6613            TimestampMillisecondArray::from(vec![Some(864000003005), Some(1545696002001), None]);
6614        let b = cast(&array, &DataType::Timestamp(TimeUnit::Second, None)).unwrap();
6615        let c = b.as_primitive::<TimestampSecondType>();
6616        assert_eq!(864000003, c.value(0));
6617        assert_eq!(1545696002, c.value(1));
6618        assert!(c.is_null(2));
6619    }
6620
6621    #[test]
6622    fn test_cast_duration_to_i64() {
6623        let base = vec![5, 6, 7, 8, 100000000];
6624
6625        let duration_arrays = vec![
6626            Arc::new(DurationNanosecondArray::from(base.clone())) as ArrayRef,
6627            Arc::new(DurationMicrosecondArray::from(base.clone())) as ArrayRef,
6628            Arc::new(DurationMillisecondArray::from(base.clone())) as ArrayRef,
6629            Arc::new(DurationSecondArray::from(base.clone())) as ArrayRef,
6630        ];
6631
6632        for arr in duration_arrays {
6633            assert!(can_cast_types(arr.data_type(), &DataType::Int64));
6634            let result = cast(&arr, &DataType::Int64).unwrap();
6635            let result = result.as_primitive::<Int64Type>();
6636            assert_eq!(base.as_slice(), result.values());
6637        }
6638    }
6639
6640    #[test]
6641    fn test_cast_between_durations_and_numerics() {
6642        fn test_cast_between_durations<FromType, ToType>()
6643        where
6644            FromType: ArrowPrimitiveType<Native = i64>,
6645            ToType: ArrowPrimitiveType<Native = i64>,
6646            PrimitiveArray<FromType>: From<Vec<Option<i64>>>,
6647        {
6648            let DataType::Duration(from_unit) = FromType::DATA_TYPE else {
6649                panic!("Expected a duration type")
6650            };
6651            let DataType::Duration(to_unit) = ToType::DATA_TYPE else {
6652                panic!("Expected a duration type")
6653            };
6654            let from_size = time_unit_multiple(&from_unit);
6655            let to_size = time_unit_multiple(&to_unit);
6656
6657            let (v1_before, v2_before) = (8640003005, 1696002001);
6658            let (v1_after, v2_after) = if from_size >= to_size {
6659                (
6660                    v1_before / (from_size / to_size),
6661                    v2_before / (from_size / to_size),
6662                )
6663            } else {
6664                (
6665                    v1_before * (to_size / from_size),
6666                    v2_before * (to_size / from_size),
6667                )
6668            };
6669
6670            let array =
6671                PrimitiveArray::<FromType>::from(vec![Some(v1_before), Some(v2_before), None]);
6672            let b = cast(&array, &ToType::DATA_TYPE).unwrap();
6673            let c = b.as_primitive::<ToType>();
6674            assert_eq!(v1_after, c.value(0));
6675            assert_eq!(v2_after, c.value(1));
6676            assert!(c.is_null(2));
6677        }
6678
6679        // between each individual duration type
6680        test_cast_between_durations::<DurationSecondType, DurationMillisecondType>();
6681        test_cast_between_durations::<DurationSecondType, DurationMicrosecondType>();
6682        test_cast_between_durations::<DurationSecondType, DurationNanosecondType>();
6683        test_cast_between_durations::<DurationMillisecondType, DurationSecondType>();
6684        test_cast_between_durations::<DurationMillisecondType, DurationMicrosecondType>();
6685        test_cast_between_durations::<DurationMillisecondType, DurationNanosecondType>();
6686        test_cast_between_durations::<DurationMicrosecondType, DurationSecondType>();
6687        test_cast_between_durations::<DurationMicrosecondType, DurationMillisecondType>();
6688        test_cast_between_durations::<DurationMicrosecondType, DurationNanosecondType>();
6689        test_cast_between_durations::<DurationNanosecondType, DurationSecondType>();
6690        test_cast_between_durations::<DurationNanosecondType, DurationMillisecondType>();
6691        test_cast_between_durations::<DurationNanosecondType, DurationMicrosecondType>();
6692
6693        // cast failed
6694        let array = DurationSecondArray::from(vec![
6695            Some(i64::MAX),
6696            Some(8640203410378005),
6697            Some(10241096),
6698            None,
6699        ]);
6700        let b = cast(&array, &DataType::Duration(TimeUnit::Nanosecond)).unwrap();
6701        let c = b.as_primitive::<DurationNanosecondType>();
6702        assert!(c.is_null(0));
6703        assert!(c.is_null(1));
6704        assert_eq!(10241096000000000, c.value(2));
6705        assert!(c.is_null(3));
6706
6707        // durations to numerics
6708        let array = DurationSecondArray::from(vec![
6709            Some(i64::MAX),
6710            Some(8640203410378005),
6711            Some(10241096),
6712            None,
6713        ]);
6714        let b = cast(&array, &DataType::Int64).unwrap();
6715        let c = b.as_primitive::<Int64Type>();
6716        assert_eq!(i64::MAX, c.value(0));
6717        assert_eq!(8640203410378005, c.value(1));
6718        assert_eq!(10241096, c.value(2));
6719        assert!(c.is_null(3));
6720
6721        let b = cast(&array, &DataType::Int32).unwrap();
6722        let c = b.as_primitive::<Int32Type>();
6723        assert_eq!(0, c.value(0));
6724        assert_eq!(0, c.value(1));
6725        assert_eq!(10241096, c.value(2));
6726        assert!(c.is_null(3));
6727
6728        // numerics to durations
6729        let array = Int32Array::from(vec![Some(i32::MAX), Some(802034103), Some(10241096), None]);
6730        let b = cast(&array, &DataType::Duration(TimeUnit::Second)).unwrap();
6731        let c = b.as_any().downcast_ref::<DurationSecondArray>().unwrap();
6732        assert_eq!(i32::MAX as i64, c.value(0));
6733        assert_eq!(802034103, c.value(1));
6734        assert_eq!(10241096, c.value(2));
6735        assert!(c.is_null(3));
6736    }
6737
6738    #[test]
6739    fn test_cast_to_strings() {
6740        let a = Int32Array::from(vec![1, 2, 3]);
6741        let out = cast(&a, &DataType::Utf8).unwrap();
6742        let out = out
6743            .as_any()
6744            .downcast_ref::<StringArray>()
6745            .unwrap()
6746            .into_iter()
6747            .collect::<Vec<_>>();
6748        assert_eq!(out, vec![Some("1"), Some("2"), Some("3")]);
6749        let out = cast(&a, &DataType::LargeUtf8).unwrap();
6750        let out = out
6751            .as_any()
6752            .downcast_ref::<LargeStringArray>()
6753            .unwrap()
6754            .into_iter()
6755            .collect::<Vec<_>>();
6756        assert_eq!(out, vec![Some("1"), Some("2"), Some("3")]);
6757    }
6758
6759    #[test]
6760    fn test_str_to_str_casts() {
6761        for data in [
6762            vec![Some("foo"), Some("bar"), Some("ham")],
6763            vec![Some("foo"), None, Some("bar")],
6764        ] {
6765            let a = LargeStringArray::from(data.clone());
6766            let to = cast(&a, &DataType::Utf8).unwrap();
6767            let expect = a
6768                .as_any()
6769                .downcast_ref::<LargeStringArray>()
6770                .unwrap()
6771                .into_iter()
6772                .collect::<Vec<_>>();
6773            let out = to
6774                .as_any()
6775                .downcast_ref::<StringArray>()
6776                .unwrap()
6777                .into_iter()
6778                .collect::<Vec<_>>();
6779            assert_eq!(expect, out);
6780
6781            let a = StringArray::from(data);
6782            let to = cast(&a, &DataType::LargeUtf8).unwrap();
6783            let expect = a
6784                .as_any()
6785                .downcast_ref::<StringArray>()
6786                .unwrap()
6787                .into_iter()
6788                .collect::<Vec<_>>();
6789            let out = to
6790                .as_any()
6791                .downcast_ref::<LargeStringArray>()
6792                .unwrap()
6793                .into_iter()
6794                .collect::<Vec<_>>();
6795            assert_eq!(expect, out);
6796        }
6797    }
6798
6799    const VIEW_TEST_DATA: [Option<&str>; 5] = [
6800        Some("hello"),
6801        Some("repeated"),
6802        None,
6803        Some("large payload over 12 bytes"),
6804        Some("repeated"),
6805    ];
6806
6807    #[test]
6808    fn test_string_view_to_binary_view() {
6809        let string_view_array = StringViewArray::from_iter(VIEW_TEST_DATA);
6810
6811        assert!(can_cast_types(
6812            string_view_array.data_type(),
6813            &DataType::BinaryView
6814        ));
6815
6816        let binary_view_array = cast(&string_view_array, &DataType::BinaryView).unwrap();
6817        assert_eq!(binary_view_array.data_type(), &DataType::BinaryView);
6818
6819        let expect_binary_view_array = BinaryViewArray::from_iter(VIEW_TEST_DATA);
6820        assert_eq!(binary_view_array.as_ref(), &expect_binary_view_array);
6821    }
6822
6823    #[test]
6824    fn test_binary_view_to_string_view() {
6825        let binary_view_array = BinaryViewArray::from_iter(VIEW_TEST_DATA);
6826
6827        assert!(can_cast_types(
6828            binary_view_array.data_type(),
6829            &DataType::Utf8View
6830        ));
6831
6832        let string_view_array = cast(&binary_view_array, &DataType::Utf8View).unwrap();
6833        assert_eq!(string_view_array.data_type(), &DataType::Utf8View);
6834
6835        let expect_string_view_array = StringViewArray::from_iter(VIEW_TEST_DATA);
6836        assert_eq!(string_view_array.as_ref(), &expect_string_view_array);
6837    }
6838
6839    #[test]
6840    fn test_binary_view_to_string_view_with_invalid_utf8() {
6841        let binary_view_array = BinaryViewArray::from_iter(vec![
6842            Some(b"valid".as_slice()),
6843            Some(&[0xff]),
6844            Some(b"utf8".as_slice()),
6845            None,
6846        ]);
6847
6848        let strict_options = CastOptions {
6849            safe: false,
6850            ..Default::default()
6851        };
6852
6853        assert!(
6854            cast_with_options(&binary_view_array, &DataType::Utf8View, &strict_options).is_err()
6855        );
6856
6857        let safe_options = CastOptions {
6858            safe: true,
6859            ..Default::default()
6860        };
6861
6862        let string_view_array =
6863            cast_with_options(&binary_view_array, &DataType::Utf8View, &safe_options).unwrap();
6864        assert_eq!(string_view_array.data_type(), &DataType::Utf8View);
6865
6866        let values: Vec<_> = string_view_array.as_string_view().iter().collect();
6867
6868        assert_eq!(values, vec![Some("valid"), None, Some("utf8"), None]);
6869    }
6870
6871    #[test]
6872    fn test_string_to_view() {
6873        _test_string_to_view::<i32>();
6874        _test_string_to_view::<i64>();
6875    }
6876
6877    fn _test_string_to_view<O>()
6878    where
6879        O: OffsetSizeTrait,
6880    {
6881        let string_array = GenericStringArray::<O>::from_iter(VIEW_TEST_DATA);
6882
6883        assert!(can_cast_types(
6884            string_array.data_type(),
6885            &DataType::Utf8View
6886        ));
6887
6888        assert!(can_cast_types(
6889            string_array.data_type(),
6890            &DataType::BinaryView
6891        ));
6892
6893        let string_view_array = cast(&string_array, &DataType::Utf8View).unwrap();
6894        assert_eq!(string_view_array.data_type(), &DataType::Utf8View);
6895
6896        let binary_view_array = cast(&string_array, &DataType::BinaryView).unwrap();
6897        assert_eq!(binary_view_array.data_type(), &DataType::BinaryView);
6898
6899        let expect_string_view_array = StringViewArray::from_iter(VIEW_TEST_DATA);
6900        assert_eq!(string_view_array.as_ref(), &expect_string_view_array);
6901
6902        let expect_binary_view_array = BinaryViewArray::from_iter(VIEW_TEST_DATA);
6903        assert_eq!(binary_view_array.as_ref(), &expect_binary_view_array);
6904    }
6905
6906    #[test]
6907    fn test_binary_to_view() {
6908        _test_binary_to_view::<i32>();
6909        _test_binary_to_view::<i64>();
6910    }
6911
6912    fn _test_binary_to_view<O>()
6913    where
6914        O: OffsetSizeTrait,
6915    {
6916        let binary_array = GenericBinaryArray::<O>::from_iter(VIEW_TEST_DATA);
6917
6918        assert!(can_cast_types(
6919            binary_array.data_type(),
6920            &DataType::Utf8View
6921        ));
6922
6923        assert!(can_cast_types(
6924            binary_array.data_type(),
6925            &DataType::BinaryView
6926        ));
6927
6928        let string_view_array = cast(&binary_array, &DataType::Utf8View).unwrap();
6929        assert_eq!(string_view_array.data_type(), &DataType::Utf8View);
6930
6931        let binary_view_array = cast(&binary_array, &DataType::BinaryView).unwrap();
6932        assert_eq!(binary_view_array.data_type(), &DataType::BinaryView);
6933
6934        let expect_string_view_array = StringViewArray::from_iter(VIEW_TEST_DATA);
6935        assert_eq!(string_view_array.as_ref(), &expect_string_view_array);
6936
6937        let expect_binary_view_array = BinaryViewArray::from_iter(VIEW_TEST_DATA);
6938        assert_eq!(binary_view_array.as_ref(), &expect_binary_view_array);
6939    }
6940
6941    #[test]
6942    fn test_dict_to_view() {
6943        let values = StringArray::from_iter(VIEW_TEST_DATA);
6944        let keys = Int8Array::from_iter([Some(1), Some(0), None, Some(3), None, Some(1), Some(4)]);
6945        let string_dict_array =
6946            DictionaryArray::<Int8Type>::try_new(keys, Arc::new(values)).unwrap();
6947        let typed_dict = string_dict_array.downcast_dict::<StringArray>().unwrap();
6948
6949        let string_view_array = {
6950            let mut builder = StringViewBuilder::new().with_fixed_block_size(8); // multiple buffers.
6951            for v in typed_dict {
6952                builder.append_option(v);
6953            }
6954            builder.finish()
6955        };
6956        let expected_string_array_type = string_view_array.data_type();
6957        let casted_string_array = cast(&string_dict_array, expected_string_array_type).unwrap();
6958        assert_eq!(casted_string_array.data_type(), expected_string_array_type);
6959        assert_eq!(casted_string_array.as_ref(), &string_view_array);
6960
6961        let binary_buffer = cast(&typed_dict.values(), &DataType::Binary).unwrap();
6962        let binary_dict_array =
6963            DictionaryArray::<Int8Type>::new(typed_dict.keys().clone(), binary_buffer);
6964        let typed_binary_dict = binary_dict_array.downcast_dict::<BinaryArray>().unwrap();
6965
6966        let binary_view_array = {
6967            let mut builder = BinaryViewBuilder::new().with_fixed_block_size(8); // multiple buffers.
6968            for v in typed_binary_dict {
6969                builder.append_option(v);
6970            }
6971            builder.finish()
6972        };
6973        let expected_binary_array_type = binary_view_array.data_type();
6974        let casted_binary_array = cast(&binary_dict_array, expected_binary_array_type).unwrap();
6975        assert_eq!(casted_binary_array.data_type(), expected_binary_array_type);
6976        assert_eq!(casted_binary_array.as_ref(), &binary_view_array);
6977    }
6978
6979    #[test]
6980    fn test_dict_to_view_null_dictionary_value_is_null() {
6981        // Ensure we preserve nulls in the values
6982        let keys = Int32Array::from_iter([Some(0), Some(1), Some(2), None, Some(1)]);
6983
6984        let values = StringArray::from(vec![Some("aa"), None, Some("a value over twelve bytes")]);
6985        let dict = DictionaryArray::<Int32Type>::try_new(keys.clone(), Arc::new(values)).unwrap();
6986        let casted = cast(&dict, &DataType::Utf8View).unwrap();
6987        assert_eq!(
6988            casted.as_string_view().iter().collect::<Vec<_>>(),
6989            vec![
6990                Some("aa"),
6991                None,
6992                Some("a value over twelve bytes"),
6993                None,
6994                None
6995            ]
6996        );
6997        // the same input cast to Utf8 goes through `unpack_dictionary` and always agreed
6998        let reference = cast(&dict, &DataType::Utf8).unwrap();
6999        assert_eq!(
7000            casted.as_string_view().iter().collect::<Vec<_>>(),
7001            reference.as_string::<i32>().iter().collect::<Vec<_>>()
7002        );
7003
7004        let values = BinaryArray::from_opt_vec(vec![
7005            Some(b"aa".as_slice()),
7006            None,
7007            Some(b"a value over twelve bytes"),
7008        ]);
7009        let dict = DictionaryArray::<Int32Type>::try_new(keys, Arc::new(values)).unwrap();
7010        let casted = cast(&dict, &DataType::BinaryView).unwrap();
7011        assert_eq!(
7012            casted.as_binary_view().iter().collect::<Vec<_>>(),
7013            vec![
7014                Some(b"aa".as_slice()),
7015                None,
7016                Some(b"a value over twelve bytes"),
7017                None,
7018                None
7019            ]
7020        );
7021    }
7022
7023    #[test]
7024    fn test_view_to_dict() {
7025        let string_view_array = StringViewArray::from_iter(VIEW_TEST_DATA);
7026        let string_dict_array: DictionaryArray<Int8Type> = VIEW_TEST_DATA.into_iter().collect();
7027        let casted_type = string_dict_array.data_type();
7028        let casted_dict_array = cast(&string_view_array, casted_type).unwrap();
7029        assert_eq!(casted_dict_array.data_type(), casted_type);
7030        assert_eq!(casted_dict_array.as_ref(), &string_dict_array);
7031
7032        let binary_view_array = BinaryViewArray::from_iter(VIEW_TEST_DATA);
7033        let binary_dict_array = string_dict_array.downcast_dict::<StringArray>().unwrap();
7034        let binary_buffer = cast(&binary_dict_array.values(), &DataType::Binary).unwrap();
7035        let binary_dict_array =
7036            DictionaryArray::<Int8Type>::new(binary_dict_array.keys().clone(), binary_buffer);
7037        let casted_type = binary_dict_array.data_type();
7038        let casted_binary_array = cast(&binary_view_array, casted_type).unwrap();
7039        assert_eq!(casted_binary_array.data_type(), casted_type);
7040        assert_eq!(casted_binary_array.as_ref(), &binary_dict_array);
7041    }
7042
7043    #[test]
7044    fn test_view_to_string() {
7045        _test_view_to_string::<i32>();
7046        _test_view_to_string::<i64>();
7047    }
7048
7049    fn _test_view_to_string<O>()
7050    where
7051        O: OffsetSizeTrait,
7052    {
7053        let string_view_array = {
7054            let mut builder = StringViewBuilder::new().with_fixed_block_size(8); // multiple buffers.
7055            for s in &VIEW_TEST_DATA {
7056                builder.append_option(*s);
7057            }
7058            builder.finish()
7059        };
7060
7061        let binary_view_array = BinaryViewArray::from_iter(VIEW_TEST_DATA);
7062
7063        let expected_string_array = GenericStringArray::<O>::from_iter(VIEW_TEST_DATA);
7064        let expected_type = expected_string_array.data_type();
7065
7066        assert!(can_cast_types(string_view_array.data_type(), expected_type));
7067        assert!(can_cast_types(binary_view_array.data_type(), expected_type));
7068
7069        let string_view_casted_array = cast(&string_view_array, expected_type).unwrap();
7070        assert_eq!(string_view_casted_array.data_type(), expected_type);
7071        assert_eq!(string_view_casted_array.as_ref(), &expected_string_array);
7072
7073        let binary_view_casted_array = cast(&binary_view_array, expected_type).unwrap();
7074        assert_eq!(binary_view_casted_array.data_type(), expected_type);
7075        assert_eq!(binary_view_casted_array.as_ref(), &expected_string_array);
7076    }
7077
7078    #[test]
7079    fn test_view_to_binary() {
7080        _test_view_to_binary::<i32>();
7081        _test_view_to_binary::<i64>();
7082    }
7083
7084    fn _test_view_to_binary<O>()
7085    where
7086        O: OffsetSizeTrait,
7087    {
7088        let view_array = {
7089            let mut builder = BinaryViewBuilder::new().with_fixed_block_size(8); // multiple buffers.
7090            for s in &VIEW_TEST_DATA {
7091                builder.append_option(*s);
7092            }
7093            builder.finish()
7094        };
7095
7096        let expected_binary_array = GenericBinaryArray::<O>::from_iter(VIEW_TEST_DATA);
7097        let expected_type = expected_binary_array.data_type();
7098
7099        assert!(can_cast_types(view_array.data_type(), expected_type));
7100
7101        let binary_array = cast(&view_array, expected_type).unwrap();
7102        assert_eq!(binary_array.data_type(), expected_type);
7103
7104        assert_eq!(binary_array.as_ref(), &expected_binary_array);
7105    }
7106
7107    #[test]
7108    #[cfg_attr(miri, ignore)] // Unsupported inline assembly
7109    fn test_cast_from_f64() {
7110        let f64_values: Vec<f64> = vec![
7111            i64::MIN as f64,
7112            i32::MIN as f64,
7113            i16::MIN as f64,
7114            i8::MIN as f64,
7115            0_f64,
7116            u8::MAX as f64,
7117            u16::MAX as f64,
7118            u32::MAX as f64,
7119            u64::MAX as f64,
7120        ];
7121        let f64_array: ArrayRef = Arc::new(Float64Array::from(f64_values));
7122
7123        let f64_expected = vec![
7124            -9223372036854776000.0,
7125            -2147483648.0,
7126            -32768.0,
7127            -128.0,
7128            0.0,
7129            255.0,
7130            65535.0,
7131            4294967295.0,
7132            18446744073709552000.0,
7133        ];
7134        assert_eq!(
7135            f64_expected,
7136            get_cast_values::<Float64Type>(&f64_array, &DataType::Float64)
7137                .iter()
7138                .map(|i| i.parse::<f64>().unwrap())
7139                .collect::<Vec<f64>>()
7140        );
7141
7142        let f32_expected = vec![
7143            -9223372000000000000.0,
7144            -2147483600.0,
7145            -32768.0,
7146            -128.0,
7147            0.0,
7148            255.0,
7149            65535.0,
7150            4294967300.0,
7151            18446744000000000000.0,
7152        ];
7153        assert_eq!(
7154            f32_expected,
7155            get_cast_values::<Float32Type>(&f64_array, &DataType::Float32)
7156                .iter()
7157                .map(|i| i.parse::<f32>().unwrap())
7158                .collect::<Vec<f32>>()
7159        );
7160
7161        let f16_expected = vec![
7162            f16::from_f64(-9223372000000000000.0),
7163            f16::from_f64(-2147483600.0),
7164            f16::from_f64(-32768.0),
7165            f16::from_f64(-128.0),
7166            f16::from_f64(0.0),
7167            f16::from_f64(255.0),
7168            f16::from_f64(65535.0),
7169            f16::from_f64(4294967300.0),
7170            f16::from_f64(18446744000000000000.0),
7171        ];
7172        assert_eq!(
7173            f16_expected,
7174            get_cast_values::<Float16Type>(&f64_array, &DataType::Float16)
7175                .iter()
7176                .map(|i| i.parse::<f16>().unwrap())
7177                .collect::<Vec<f16>>()
7178        );
7179
7180        let i64_expected = vec![
7181            "-9223372036854775808",
7182            "-2147483648",
7183            "-32768",
7184            "-128",
7185            "0",
7186            "255",
7187            "65535",
7188            "4294967295",
7189            "null",
7190        ];
7191        assert_eq!(
7192            i64_expected,
7193            get_cast_values::<Int64Type>(&f64_array, &DataType::Int64)
7194        );
7195
7196        let i32_expected = vec![
7197            "null",
7198            "-2147483648",
7199            "-32768",
7200            "-128",
7201            "0",
7202            "255",
7203            "65535",
7204            "null",
7205            "null",
7206        ];
7207        assert_eq!(
7208            i32_expected,
7209            get_cast_values::<Int32Type>(&f64_array, &DataType::Int32)
7210        );
7211
7212        let i16_expected = vec![
7213            "null", "null", "-32768", "-128", "0", "255", "null", "null", "null",
7214        ];
7215        assert_eq!(
7216            i16_expected,
7217            get_cast_values::<Int16Type>(&f64_array, &DataType::Int16)
7218        );
7219
7220        let i8_expected = vec![
7221            "null", "null", "null", "-128", "0", "null", "null", "null", "null",
7222        ];
7223        assert_eq!(
7224            i8_expected,
7225            get_cast_values::<Int8Type>(&f64_array, &DataType::Int8)
7226        );
7227
7228        let u64_expected = vec![
7229            "null",
7230            "null",
7231            "null",
7232            "null",
7233            "0",
7234            "255",
7235            "65535",
7236            "4294967295",
7237            "null",
7238        ];
7239        assert_eq!(
7240            u64_expected,
7241            get_cast_values::<UInt64Type>(&f64_array, &DataType::UInt64)
7242        );
7243
7244        let u32_expected = vec![
7245            "null",
7246            "null",
7247            "null",
7248            "null",
7249            "0",
7250            "255",
7251            "65535",
7252            "4294967295",
7253            "null",
7254        ];
7255        assert_eq!(
7256            u32_expected,
7257            get_cast_values::<UInt32Type>(&f64_array, &DataType::UInt32)
7258        );
7259
7260        let u16_expected = vec![
7261            "null", "null", "null", "null", "0", "255", "65535", "null", "null",
7262        ];
7263        assert_eq!(
7264            u16_expected,
7265            get_cast_values::<UInt16Type>(&f64_array, &DataType::UInt16)
7266        );
7267
7268        let u8_expected = vec![
7269            "null", "null", "null", "null", "0", "255", "null", "null", "null",
7270        ];
7271        assert_eq!(
7272            u8_expected,
7273            get_cast_values::<UInt8Type>(&f64_array, &DataType::UInt8)
7274        );
7275    }
7276
7277    #[test]
7278    #[cfg_attr(miri, ignore)] // Unsupported inline assembly
7279    fn test_cast_from_f32() {
7280        let f32_values: Vec<f32> = vec![
7281            i32::MIN as f32,
7282            i32::MIN as f32,
7283            i16::MIN as f32,
7284            i8::MIN as f32,
7285            0_f32,
7286            u8::MAX as f32,
7287            u16::MAX as f32,
7288            u32::MAX as f32,
7289            u32::MAX as f32,
7290        ];
7291        let f32_array: ArrayRef = Arc::new(Float32Array::from(f32_values));
7292
7293        let f64_expected = vec![
7294            "-2147483648.0",
7295            "-2147483648.0",
7296            "-32768.0",
7297            "-128.0",
7298            "0.0",
7299            "255.0",
7300            "65535.0",
7301            "4294967296.0",
7302            "4294967296.0",
7303        ];
7304        assert_eq!(
7305            f64_expected,
7306            get_cast_values::<Float64Type>(&f32_array, &DataType::Float64)
7307        );
7308
7309        let f32_expected = vec![
7310            "-2147483600.0",
7311            "-2147483600.0",
7312            "-32768.0",
7313            "-128.0",
7314            "0.0",
7315            "255.0",
7316            "65535.0",
7317            "4294967300.0",
7318            "4294967300.0",
7319        ];
7320        assert_eq!(
7321            f32_expected,
7322            get_cast_values::<Float32Type>(&f32_array, &DataType::Float32)
7323        );
7324
7325        let f16_expected = vec![
7326            "-inf", "-inf", "-32768.0", "-128.0", "0.0", "255.0", "inf", "inf", "inf",
7327        ];
7328        assert_eq!(
7329            f16_expected,
7330            get_cast_values::<Float16Type>(&f32_array, &DataType::Float16)
7331        );
7332
7333        let i64_expected = vec![
7334            "-2147483648",
7335            "-2147483648",
7336            "-32768",
7337            "-128",
7338            "0",
7339            "255",
7340            "65535",
7341            "4294967296",
7342            "4294967296",
7343        ];
7344        assert_eq!(
7345            i64_expected,
7346            get_cast_values::<Int64Type>(&f32_array, &DataType::Int64)
7347        );
7348
7349        let i32_expected = vec![
7350            "-2147483648",
7351            "-2147483648",
7352            "-32768",
7353            "-128",
7354            "0",
7355            "255",
7356            "65535",
7357            "null",
7358            "null",
7359        ];
7360        assert_eq!(
7361            i32_expected,
7362            get_cast_values::<Int32Type>(&f32_array, &DataType::Int32)
7363        );
7364
7365        let i16_expected = vec![
7366            "null", "null", "-32768", "-128", "0", "255", "null", "null", "null",
7367        ];
7368        assert_eq!(
7369            i16_expected,
7370            get_cast_values::<Int16Type>(&f32_array, &DataType::Int16)
7371        );
7372
7373        let i8_expected = vec![
7374            "null", "null", "null", "-128", "0", "null", "null", "null", "null",
7375        ];
7376        assert_eq!(
7377            i8_expected,
7378            get_cast_values::<Int8Type>(&f32_array, &DataType::Int8)
7379        );
7380
7381        let u64_expected = vec![
7382            "null",
7383            "null",
7384            "null",
7385            "null",
7386            "0",
7387            "255",
7388            "65535",
7389            "4294967296",
7390            "4294967296",
7391        ];
7392        assert_eq!(
7393            u64_expected,
7394            get_cast_values::<UInt64Type>(&f32_array, &DataType::UInt64)
7395        );
7396
7397        let u32_expected = vec![
7398            "null", "null", "null", "null", "0", "255", "65535", "null", "null",
7399        ];
7400        assert_eq!(
7401            u32_expected,
7402            get_cast_values::<UInt32Type>(&f32_array, &DataType::UInt32)
7403        );
7404
7405        let u16_expected = vec![
7406            "null", "null", "null", "null", "0", "255", "65535", "null", "null",
7407        ];
7408        assert_eq!(
7409            u16_expected,
7410            get_cast_values::<UInt16Type>(&f32_array, &DataType::UInt16)
7411        );
7412
7413        let u8_expected = vec![
7414            "null", "null", "null", "null", "0", "255", "null", "null", "null",
7415        ];
7416        assert_eq!(
7417            u8_expected,
7418            get_cast_values::<UInt8Type>(&f32_array, &DataType::UInt8)
7419        );
7420    }
7421
7422    #[test]
7423    #[cfg_attr(miri, ignore)] // Unsupported inline assembly
7424    fn test_cast_from_uint64() {
7425        let u64_values: Vec<u64> = vec![
7426            0,
7427            u8::MAX as u64,
7428            u16::MAX as u64,
7429            u32::MAX as u64,
7430            u64::MAX,
7431        ];
7432        let u64_array: ArrayRef = Arc::new(UInt64Array::from(u64_values));
7433
7434        let f64_expected = vec![0.0, 255.0, 65535.0, 4294967295.0, 18446744073709552000.0];
7435        assert_eq!(
7436            f64_expected,
7437            get_cast_values::<Float64Type>(&u64_array, &DataType::Float64)
7438                .iter()
7439                .map(|i| i.parse::<f64>().unwrap())
7440                .collect::<Vec<f64>>()
7441        );
7442
7443        let f32_expected = vec![0.0, 255.0, 65535.0, 4294967300.0, 18446744000000000000.0];
7444        assert_eq!(
7445            f32_expected,
7446            get_cast_values::<Float32Type>(&u64_array, &DataType::Float32)
7447                .iter()
7448                .map(|i| i.parse::<f32>().unwrap())
7449                .collect::<Vec<f32>>()
7450        );
7451
7452        let f16_expected = vec![
7453            f16::from_f64(0.0),
7454            f16::from_f64(255.0),
7455            f16::from_f64(65535.0),
7456            f16::from_f64(4294967300.0),
7457            f16::from_f64(18446744000000000000.0),
7458        ];
7459        assert_eq!(
7460            f16_expected,
7461            get_cast_values::<Float16Type>(&u64_array, &DataType::Float16)
7462                .iter()
7463                .map(|i| i.parse::<f16>().unwrap())
7464                .collect::<Vec<f16>>()
7465        );
7466
7467        let i64_expected = vec!["0", "255", "65535", "4294967295", "null"];
7468        assert_eq!(
7469            i64_expected,
7470            get_cast_values::<Int64Type>(&u64_array, &DataType::Int64)
7471        );
7472
7473        let i32_expected = vec!["0", "255", "65535", "null", "null"];
7474        assert_eq!(
7475            i32_expected,
7476            get_cast_values::<Int32Type>(&u64_array, &DataType::Int32)
7477        );
7478
7479        let i16_expected = vec!["0", "255", "null", "null", "null"];
7480        assert_eq!(
7481            i16_expected,
7482            get_cast_values::<Int16Type>(&u64_array, &DataType::Int16)
7483        );
7484
7485        let i8_expected = vec!["0", "null", "null", "null", "null"];
7486        assert_eq!(
7487            i8_expected,
7488            get_cast_values::<Int8Type>(&u64_array, &DataType::Int8)
7489        );
7490
7491        let u64_expected = vec!["0", "255", "65535", "4294967295", "18446744073709551615"];
7492        assert_eq!(
7493            u64_expected,
7494            get_cast_values::<UInt64Type>(&u64_array, &DataType::UInt64)
7495        );
7496
7497        let u32_expected = vec!["0", "255", "65535", "4294967295", "null"];
7498        assert_eq!(
7499            u32_expected,
7500            get_cast_values::<UInt32Type>(&u64_array, &DataType::UInt32)
7501        );
7502
7503        let u16_expected = vec!["0", "255", "65535", "null", "null"];
7504        assert_eq!(
7505            u16_expected,
7506            get_cast_values::<UInt16Type>(&u64_array, &DataType::UInt16)
7507        );
7508
7509        let u8_expected = vec!["0", "255", "null", "null", "null"];
7510        assert_eq!(
7511            u8_expected,
7512            get_cast_values::<UInt8Type>(&u64_array, &DataType::UInt8)
7513        );
7514    }
7515
7516    #[test]
7517    #[cfg_attr(miri, ignore)] // Unsupported inline assembly
7518    fn test_cast_from_uint32() {
7519        let u32_values: Vec<u32> = vec![0, u8::MAX as u32, u16::MAX as u32, u32::MAX];
7520        let u32_array: ArrayRef = Arc::new(UInt32Array::from(u32_values));
7521
7522        let f64_expected = vec!["0.0", "255.0", "65535.0", "4294967295.0"];
7523        assert_eq!(
7524            f64_expected,
7525            get_cast_values::<Float64Type>(&u32_array, &DataType::Float64)
7526        );
7527
7528        let f32_expected = vec!["0.0", "255.0", "65535.0", "4294967300.0"];
7529        assert_eq!(
7530            f32_expected,
7531            get_cast_values::<Float32Type>(&u32_array, &DataType::Float32)
7532        );
7533
7534        let f16_expected = vec!["0.0", "255.0", "inf", "inf"];
7535        assert_eq!(
7536            f16_expected,
7537            get_cast_values::<Float16Type>(&u32_array, &DataType::Float16)
7538        );
7539
7540        let i64_expected = vec!["0", "255", "65535", "4294967295"];
7541        assert_eq!(
7542            i64_expected,
7543            get_cast_values::<Int64Type>(&u32_array, &DataType::Int64)
7544        );
7545
7546        let i32_expected = vec!["0", "255", "65535", "null"];
7547        assert_eq!(
7548            i32_expected,
7549            get_cast_values::<Int32Type>(&u32_array, &DataType::Int32)
7550        );
7551
7552        let i16_expected = vec!["0", "255", "null", "null"];
7553        assert_eq!(
7554            i16_expected,
7555            get_cast_values::<Int16Type>(&u32_array, &DataType::Int16)
7556        );
7557
7558        let i8_expected = vec!["0", "null", "null", "null"];
7559        assert_eq!(
7560            i8_expected,
7561            get_cast_values::<Int8Type>(&u32_array, &DataType::Int8)
7562        );
7563
7564        let u64_expected = vec!["0", "255", "65535", "4294967295"];
7565        assert_eq!(
7566            u64_expected,
7567            get_cast_values::<UInt64Type>(&u32_array, &DataType::UInt64)
7568        );
7569
7570        let u32_expected = vec!["0", "255", "65535", "4294967295"];
7571        assert_eq!(
7572            u32_expected,
7573            get_cast_values::<UInt32Type>(&u32_array, &DataType::UInt32)
7574        );
7575
7576        let u16_expected = vec!["0", "255", "65535", "null"];
7577        assert_eq!(
7578            u16_expected,
7579            get_cast_values::<UInt16Type>(&u32_array, &DataType::UInt16)
7580        );
7581
7582        let u8_expected = vec!["0", "255", "null", "null"];
7583        assert_eq!(
7584            u8_expected,
7585            get_cast_values::<UInt8Type>(&u32_array, &DataType::UInt8)
7586        );
7587    }
7588
7589    #[test]
7590    #[cfg_attr(miri, ignore)] // Unsupported inline assembly
7591    fn test_cast_from_uint16() {
7592        let u16_values: Vec<u16> = vec![0, u8::MAX as u16, u16::MAX];
7593        let u16_array: ArrayRef = Arc::new(UInt16Array::from(u16_values));
7594
7595        let f64_expected = vec!["0.0", "255.0", "65535.0"];
7596        assert_eq!(
7597            f64_expected,
7598            get_cast_values::<Float64Type>(&u16_array, &DataType::Float64)
7599        );
7600
7601        let f32_expected = vec!["0.0", "255.0", "65535.0"];
7602        assert_eq!(
7603            f32_expected,
7604            get_cast_values::<Float32Type>(&u16_array, &DataType::Float32)
7605        );
7606
7607        let f16_expected = vec!["0.0", "255.0", "inf"];
7608        assert_eq!(
7609            f16_expected,
7610            get_cast_values::<Float16Type>(&u16_array, &DataType::Float16)
7611        );
7612
7613        let i64_expected = vec!["0", "255", "65535"];
7614        assert_eq!(
7615            i64_expected,
7616            get_cast_values::<Int64Type>(&u16_array, &DataType::Int64)
7617        );
7618
7619        let i32_expected = vec!["0", "255", "65535"];
7620        assert_eq!(
7621            i32_expected,
7622            get_cast_values::<Int32Type>(&u16_array, &DataType::Int32)
7623        );
7624
7625        let i16_expected = vec!["0", "255", "null"];
7626        assert_eq!(
7627            i16_expected,
7628            get_cast_values::<Int16Type>(&u16_array, &DataType::Int16)
7629        );
7630
7631        let i8_expected = vec!["0", "null", "null"];
7632        assert_eq!(
7633            i8_expected,
7634            get_cast_values::<Int8Type>(&u16_array, &DataType::Int8)
7635        );
7636
7637        let u64_expected = vec!["0", "255", "65535"];
7638        assert_eq!(
7639            u64_expected,
7640            get_cast_values::<UInt64Type>(&u16_array, &DataType::UInt64)
7641        );
7642
7643        let u32_expected = vec!["0", "255", "65535"];
7644        assert_eq!(
7645            u32_expected,
7646            get_cast_values::<UInt32Type>(&u16_array, &DataType::UInt32)
7647        );
7648
7649        let u16_expected = vec!["0", "255", "65535"];
7650        assert_eq!(
7651            u16_expected,
7652            get_cast_values::<UInt16Type>(&u16_array, &DataType::UInt16)
7653        );
7654
7655        let u8_expected = vec!["0", "255", "null"];
7656        assert_eq!(
7657            u8_expected,
7658            get_cast_values::<UInt8Type>(&u16_array, &DataType::UInt8)
7659        );
7660    }
7661
7662    #[test]
7663    #[cfg_attr(miri, ignore)] // Unsupported inline assembly
7664    fn test_cast_from_uint8() {
7665        let u8_values: Vec<u8> = vec![0, u8::MAX];
7666        let u8_array: ArrayRef = Arc::new(UInt8Array::from(u8_values));
7667
7668        let f64_expected = vec!["0.0", "255.0"];
7669        assert_eq!(
7670            f64_expected,
7671            get_cast_values::<Float64Type>(&u8_array, &DataType::Float64)
7672        );
7673
7674        let f32_expected = vec!["0.0", "255.0"];
7675        assert_eq!(
7676            f32_expected,
7677            get_cast_values::<Float32Type>(&u8_array, &DataType::Float32)
7678        );
7679
7680        let f16_expected = vec!["0.0", "255.0"];
7681        assert_eq!(
7682            f16_expected,
7683            get_cast_values::<Float16Type>(&u8_array, &DataType::Float16)
7684        );
7685
7686        let i64_expected = vec!["0", "255"];
7687        assert_eq!(
7688            i64_expected,
7689            get_cast_values::<Int64Type>(&u8_array, &DataType::Int64)
7690        );
7691
7692        let i32_expected = vec!["0", "255"];
7693        assert_eq!(
7694            i32_expected,
7695            get_cast_values::<Int32Type>(&u8_array, &DataType::Int32)
7696        );
7697
7698        let i16_expected = vec!["0", "255"];
7699        assert_eq!(
7700            i16_expected,
7701            get_cast_values::<Int16Type>(&u8_array, &DataType::Int16)
7702        );
7703
7704        let i8_expected = vec!["0", "null"];
7705        assert_eq!(
7706            i8_expected,
7707            get_cast_values::<Int8Type>(&u8_array, &DataType::Int8)
7708        );
7709
7710        let u64_expected = vec!["0", "255"];
7711        assert_eq!(
7712            u64_expected,
7713            get_cast_values::<UInt64Type>(&u8_array, &DataType::UInt64)
7714        );
7715
7716        let u32_expected = vec!["0", "255"];
7717        assert_eq!(
7718            u32_expected,
7719            get_cast_values::<UInt32Type>(&u8_array, &DataType::UInt32)
7720        );
7721
7722        let u16_expected = vec!["0", "255"];
7723        assert_eq!(
7724            u16_expected,
7725            get_cast_values::<UInt16Type>(&u8_array, &DataType::UInt16)
7726        );
7727
7728        let u8_expected = vec!["0", "255"];
7729        assert_eq!(
7730            u8_expected,
7731            get_cast_values::<UInt8Type>(&u8_array, &DataType::UInt8)
7732        );
7733    }
7734
7735    #[test]
7736    #[cfg_attr(miri, ignore)] // Unsupported inline assembly
7737    fn test_cast_from_int64() {
7738        let i64_values: Vec<i64> = vec![
7739            i64::MIN,
7740            i32::MIN as i64,
7741            i16::MIN as i64,
7742            i8::MIN as i64,
7743            0,
7744            i8::MAX as i64,
7745            i16::MAX as i64,
7746            i32::MAX as i64,
7747            i64::MAX,
7748        ];
7749        let i64_array: ArrayRef = Arc::new(Int64Array::from(i64_values));
7750
7751        let f64_expected = vec![
7752            -9223372036854776000.0,
7753            -2147483648.0,
7754            -32768.0,
7755            -128.0,
7756            0.0,
7757            127.0,
7758            32767.0,
7759            2147483647.0,
7760            9223372036854776000.0,
7761        ];
7762        assert_eq!(
7763            f64_expected,
7764            get_cast_values::<Float64Type>(&i64_array, &DataType::Float64)
7765                .iter()
7766                .map(|i| i.parse::<f64>().unwrap())
7767                .collect::<Vec<f64>>()
7768        );
7769
7770        let f32_expected = vec![
7771            -9223372000000000000.0,
7772            -2147483600.0,
7773            -32768.0,
7774            -128.0,
7775            0.0,
7776            127.0,
7777            32767.0,
7778            2147483600.0,
7779            9223372000000000000.0,
7780        ];
7781        assert_eq!(
7782            f32_expected,
7783            get_cast_values::<Float32Type>(&i64_array, &DataType::Float32)
7784                .iter()
7785                .map(|i| i.parse::<f32>().unwrap())
7786                .collect::<Vec<f32>>()
7787        );
7788
7789        let f16_expected = vec![
7790            f16::from_f64(-9223372000000000000.0),
7791            f16::from_f64(-2147483600.0),
7792            f16::from_f64(-32768.0),
7793            f16::from_f64(-128.0),
7794            f16::from_f64(0.0),
7795            f16::from_f64(127.0),
7796            f16::from_f64(32767.0),
7797            f16::from_f64(2147483600.0),
7798            f16::from_f64(9223372000000000000.0),
7799        ];
7800        assert_eq!(
7801            f16_expected,
7802            get_cast_values::<Float16Type>(&i64_array, &DataType::Float16)
7803                .iter()
7804                .map(|i| i.parse::<f16>().unwrap())
7805                .collect::<Vec<f16>>()
7806        );
7807
7808        let i64_expected = vec![
7809            "-9223372036854775808",
7810            "-2147483648",
7811            "-32768",
7812            "-128",
7813            "0",
7814            "127",
7815            "32767",
7816            "2147483647",
7817            "9223372036854775807",
7818        ];
7819        assert_eq!(
7820            i64_expected,
7821            get_cast_values::<Int64Type>(&i64_array, &DataType::Int64)
7822        );
7823
7824        let i32_expected = vec![
7825            "null",
7826            "-2147483648",
7827            "-32768",
7828            "-128",
7829            "0",
7830            "127",
7831            "32767",
7832            "2147483647",
7833            "null",
7834        ];
7835        assert_eq!(
7836            i32_expected,
7837            get_cast_values::<Int32Type>(&i64_array, &DataType::Int32)
7838        );
7839
7840        assert_eq!(
7841            i32_expected,
7842            get_cast_values::<Date32Type>(&i64_array, &DataType::Date32)
7843        );
7844
7845        let i16_expected = vec![
7846            "null", "null", "-32768", "-128", "0", "127", "32767", "null", "null",
7847        ];
7848        assert_eq!(
7849            i16_expected,
7850            get_cast_values::<Int16Type>(&i64_array, &DataType::Int16)
7851        );
7852
7853        let i8_expected = vec![
7854            "null", "null", "null", "-128", "0", "127", "null", "null", "null",
7855        ];
7856        assert_eq!(
7857            i8_expected,
7858            get_cast_values::<Int8Type>(&i64_array, &DataType::Int8)
7859        );
7860
7861        let u64_expected = vec![
7862            "null",
7863            "null",
7864            "null",
7865            "null",
7866            "0",
7867            "127",
7868            "32767",
7869            "2147483647",
7870            "9223372036854775807",
7871        ];
7872        assert_eq!(
7873            u64_expected,
7874            get_cast_values::<UInt64Type>(&i64_array, &DataType::UInt64)
7875        );
7876
7877        let u32_expected = vec![
7878            "null",
7879            "null",
7880            "null",
7881            "null",
7882            "0",
7883            "127",
7884            "32767",
7885            "2147483647",
7886            "null",
7887        ];
7888        assert_eq!(
7889            u32_expected,
7890            get_cast_values::<UInt32Type>(&i64_array, &DataType::UInt32)
7891        );
7892
7893        let u16_expected = vec![
7894            "null", "null", "null", "null", "0", "127", "32767", "null", "null",
7895        ];
7896        assert_eq!(
7897            u16_expected,
7898            get_cast_values::<UInt16Type>(&i64_array, &DataType::UInt16)
7899        );
7900
7901        let u8_expected = vec![
7902            "null", "null", "null", "null", "0", "127", "null", "null", "null",
7903        ];
7904        assert_eq!(
7905            u8_expected,
7906            get_cast_values::<UInt8Type>(&i64_array, &DataType::UInt8)
7907        );
7908    }
7909
7910    #[test]
7911    #[cfg_attr(miri, ignore)] // Unsupported inline assembly
7912    fn test_cast_from_int32() {
7913        let i32_values: Vec<i32> = vec![
7914            i32::MIN,
7915            i16::MIN as i32,
7916            i8::MIN as i32,
7917            0,
7918            i8::MAX as i32,
7919            i16::MAX as i32,
7920            i32::MAX,
7921        ];
7922        let i32_array: ArrayRef = Arc::new(Int32Array::from(i32_values));
7923
7924        let f64_expected = vec![
7925            "-2147483648.0",
7926            "-32768.0",
7927            "-128.0",
7928            "0.0",
7929            "127.0",
7930            "32767.0",
7931            "2147483647.0",
7932        ];
7933        assert_eq!(
7934            f64_expected,
7935            get_cast_values::<Float64Type>(&i32_array, &DataType::Float64)
7936        );
7937
7938        let f32_expected = vec![
7939            "-2147483600.0",
7940            "-32768.0",
7941            "-128.0",
7942            "0.0",
7943            "127.0",
7944            "32767.0",
7945            "2147483600.0",
7946        ];
7947        assert_eq!(
7948            f32_expected,
7949            get_cast_values::<Float32Type>(&i32_array, &DataType::Float32)
7950        );
7951
7952        let f16_expected = vec![
7953            f16::from_f64(-2147483600.0),
7954            f16::from_f64(-32768.0),
7955            f16::from_f64(-128.0),
7956            f16::from_f64(0.0),
7957            f16::from_f64(127.0),
7958            f16::from_f64(32767.0),
7959            f16::from_f64(2147483600.0),
7960        ];
7961        assert_eq!(
7962            f16_expected,
7963            get_cast_values::<Float16Type>(&i32_array, &DataType::Float16)
7964                .iter()
7965                .map(|i| i.parse::<f16>().unwrap())
7966                .collect::<Vec<f16>>()
7967        );
7968
7969        let i16_expected = vec!["null", "-32768", "-128", "0", "127", "32767", "null"];
7970        assert_eq!(
7971            i16_expected,
7972            get_cast_values::<Int16Type>(&i32_array, &DataType::Int16)
7973        );
7974
7975        let i8_expected = vec!["null", "null", "-128", "0", "127", "null", "null"];
7976        assert_eq!(
7977            i8_expected,
7978            get_cast_values::<Int8Type>(&i32_array, &DataType::Int8)
7979        );
7980
7981        let u64_expected = vec!["null", "null", "null", "0", "127", "32767", "2147483647"];
7982        assert_eq!(
7983            u64_expected,
7984            get_cast_values::<UInt64Type>(&i32_array, &DataType::UInt64)
7985        );
7986
7987        let u32_expected = vec!["null", "null", "null", "0", "127", "32767", "2147483647"];
7988        assert_eq!(
7989            u32_expected,
7990            get_cast_values::<UInt32Type>(&i32_array, &DataType::UInt32)
7991        );
7992
7993        let u16_expected = vec!["null", "null", "null", "0", "127", "32767", "null"];
7994        assert_eq!(
7995            u16_expected,
7996            get_cast_values::<UInt16Type>(&i32_array, &DataType::UInt16)
7997        );
7998
7999        let u8_expected = vec!["null", "null", "null", "0", "127", "null", "null"];
8000        assert_eq!(
8001            u8_expected,
8002            get_cast_values::<UInt8Type>(&i32_array, &DataType::UInt8)
8003        );
8004
8005        // The date32 to date64 cast increases the numerical values in order to keep the same dates.
8006        let i64_expected = vec![
8007            "-185542587187200000",
8008            "-2831155200000",
8009            "-11059200000",
8010            "0",
8011            "10972800000",
8012            "2831068800000",
8013            "185542587100800000",
8014        ];
8015        assert_eq!(
8016            i64_expected,
8017            get_cast_values::<Date64Type>(&i32_array, &DataType::Date64)
8018        );
8019    }
8020
8021    #[test]
8022    #[cfg_attr(miri, ignore)] // Unsupported inline assembly
8023    fn test_cast_from_int16() {
8024        let i16_values: Vec<i16> = vec![i16::MIN, i8::MIN as i16, 0, i8::MAX as i16, i16::MAX];
8025        let i16_array: ArrayRef = Arc::new(Int16Array::from(i16_values));
8026
8027        let f64_expected = vec!["-32768.0", "-128.0", "0.0", "127.0", "32767.0"];
8028        assert_eq!(
8029            f64_expected,
8030            get_cast_values::<Float64Type>(&i16_array, &DataType::Float64)
8031        );
8032
8033        let f32_expected = vec!["-32768.0", "-128.0", "0.0", "127.0", "32767.0"];
8034        assert_eq!(
8035            f32_expected,
8036            get_cast_values::<Float32Type>(&i16_array, &DataType::Float32)
8037        );
8038
8039        let f16_expected = vec![
8040            f16::from_f64(-32768.0),
8041            f16::from_f64(-128.0),
8042            f16::from_f64(0.0),
8043            f16::from_f64(127.0),
8044            f16::from_f64(32767.0),
8045        ];
8046        assert_eq!(
8047            f16_expected,
8048            get_cast_values::<Float16Type>(&i16_array, &DataType::Float16)
8049                .iter()
8050                .map(|i| i.parse::<f16>().unwrap())
8051                .collect::<Vec<f16>>()
8052        );
8053
8054        let i64_expected = vec!["-32768", "-128", "0", "127", "32767"];
8055        assert_eq!(
8056            i64_expected,
8057            get_cast_values::<Int64Type>(&i16_array, &DataType::Int64)
8058        );
8059
8060        let i32_expected = vec!["-32768", "-128", "0", "127", "32767"];
8061        assert_eq!(
8062            i32_expected,
8063            get_cast_values::<Int32Type>(&i16_array, &DataType::Int32)
8064        );
8065
8066        let i16_expected = vec!["-32768", "-128", "0", "127", "32767"];
8067        assert_eq!(
8068            i16_expected,
8069            get_cast_values::<Int16Type>(&i16_array, &DataType::Int16)
8070        );
8071
8072        let i8_expected = vec!["null", "-128", "0", "127", "null"];
8073        assert_eq!(
8074            i8_expected,
8075            get_cast_values::<Int8Type>(&i16_array, &DataType::Int8)
8076        );
8077
8078        let u64_expected = vec!["null", "null", "0", "127", "32767"];
8079        assert_eq!(
8080            u64_expected,
8081            get_cast_values::<UInt64Type>(&i16_array, &DataType::UInt64)
8082        );
8083
8084        let u32_expected = vec!["null", "null", "0", "127", "32767"];
8085        assert_eq!(
8086            u32_expected,
8087            get_cast_values::<UInt32Type>(&i16_array, &DataType::UInt32)
8088        );
8089
8090        let u16_expected = vec!["null", "null", "0", "127", "32767"];
8091        assert_eq!(
8092            u16_expected,
8093            get_cast_values::<UInt16Type>(&i16_array, &DataType::UInt16)
8094        );
8095
8096        let u8_expected = vec!["null", "null", "0", "127", "null"];
8097        assert_eq!(
8098            u8_expected,
8099            get_cast_values::<UInt8Type>(&i16_array, &DataType::UInt8)
8100        );
8101    }
8102
8103    #[test]
8104    fn test_cast_from_date32() {
8105        let i32_values: Vec<i32> = vec![
8106            i32::MIN,
8107            i16::MIN as i32,
8108            i8::MIN as i32,
8109            0,
8110            i8::MAX as i32,
8111            i16::MAX as i32,
8112            i32::MAX,
8113        ];
8114        let date32_array: ArrayRef = Arc::new(Date32Array::from(i32_values));
8115
8116        let i64_expected = vec![
8117            "-2147483648",
8118            "-32768",
8119            "-128",
8120            "0",
8121            "127",
8122            "32767",
8123            "2147483647",
8124        ];
8125        assert_eq!(
8126            i64_expected,
8127            get_cast_values::<Int64Type>(&date32_array, &DataType::Int64)
8128        );
8129    }
8130
8131    #[test]
8132    #[cfg_attr(miri, ignore)] // Unsupported inline assembly
8133    fn test_cast_from_int8() {
8134        let i8_values: Vec<i8> = vec![i8::MIN, 0, i8::MAX];
8135        let i8_array = Int8Array::from(i8_values);
8136
8137        let f64_expected = vec!["-128.0", "0.0", "127.0"];
8138        assert_eq!(
8139            f64_expected,
8140            get_cast_values::<Float64Type>(&i8_array, &DataType::Float64)
8141        );
8142
8143        let f32_expected = vec!["-128.0", "0.0", "127.0"];
8144        assert_eq!(
8145            f32_expected,
8146            get_cast_values::<Float32Type>(&i8_array, &DataType::Float32)
8147        );
8148
8149        let f16_expected = vec!["-128.0", "0.0", "127.0"];
8150        assert_eq!(
8151            f16_expected,
8152            get_cast_values::<Float16Type>(&i8_array, &DataType::Float16)
8153        );
8154
8155        let i64_expected = vec!["-128", "0", "127"];
8156        assert_eq!(
8157            i64_expected,
8158            get_cast_values::<Int64Type>(&i8_array, &DataType::Int64)
8159        );
8160
8161        let i32_expected = vec!["-128", "0", "127"];
8162        assert_eq!(
8163            i32_expected,
8164            get_cast_values::<Int32Type>(&i8_array, &DataType::Int32)
8165        );
8166
8167        let i16_expected = vec!["-128", "0", "127"];
8168        assert_eq!(
8169            i16_expected,
8170            get_cast_values::<Int16Type>(&i8_array, &DataType::Int16)
8171        );
8172
8173        let i8_expected = vec!["-128", "0", "127"];
8174        assert_eq!(
8175            i8_expected,
8176            get_cast_values::<Int8Type>(&i8_array, &DataType::Int8)
8177        );
8178
8179        let u64_expected = vec!["null", "0", "127"];
8180        assert_eq!(
8181            u64_expected,
8182            get_cast_values::<UInt64Type>(&i8_array, &DataType::UInt64)
8183        );
8184
8185        let u32_expected = vec!["null", "0", "127"];
8186        assert_eq!(
8187            u32_expected,
8188            get_cast_values::<UInt32Type>(&i8_array, &DataType::UInt32)
8189        );
8190
8191        let u16_expected = vec!["null", "0", "127"];
8192        assert_eq!(
8193            u16_expected,
8194            get_cast_values::<UInt16Type>(&i8_array, &DataType::UInt16)
8195        );
8196
8197        let u8_expected = vec!["null", "0", "127"];
8198        assert_eq!(
8199            u8_expected,
8200            get_cast_values::<UInt8Type>(&i8_array, &DataType::UInt8)
8201        );
8202    }
8203
8204    /// Convert `array` into a vector of strings by casting to data type dt
8205    fn get_cast_values<T>(array: &dyn Array, dt: &DataType) -> Vec<String>
8206    where
8207        T: ArrowPrimitiveType,
8208    {
8209        let c = cast(array, dt).unwrap();
8210        let a = c.as_primitive::<T>();
8211        let mut v: Vec<String> = vec![];
8212        for i in 0..array.len() {
8213            if a.is_null(i) {
8214                v.push("null".to_string())
8215            } else {
8216                v.push(format!("{:?}", a.value(i)));
8217            }
8218        }
8219        v
8220    }
8221
8222    #[test]
8223    fn test_cast_null_array_to_from_decimal_array() {
8224        let data_type = DataType::Decimal128(12, 4);
8225        let array = new_null_array(&DataType::Null, 4);
8226        assert_eq!(array.data_type(), &DataType::Null);
8227        let cast_array = cast(&array, &data_type).expect("cast failed");
8228        assert_eq!(cast_array.data_type(), &data_type);
8229        for i in 0..4 {
8230            assert!(cast_array.is_null(i));
8231        }
8232
8233        let array = new_null_array(&data_type, 4);
8234        assert_eq!(array.data_type(), &data_type);
8235        let cast_array = cast(&array, &DataType::Null).expect("cast failed");
8236        assert_eq!(cast_array.data_type(), &DataType::Null);
8237        assert_eq!(cast_array.len(), 4);
8238        assert_eq!(cast_array.logical_nulls().unwrap().null_count(), 4);
8239    }
8240
8241    #[test]
8242    fn test_cast_null_array_from_and_to_primitive_array() {
8243        macro_rules! typed_test {
8244            ($ARR_TYPE:ident, $DATATYPE:ident, $TYPE:tt) => {{
8245                {
8246                    let array = Arc::new(NullArray::new(6)) as ArrayRef;
8247                    let expected = $ARR_TYPE::from(vec![None; 6]);
8248                    let cast_type = DataType::$DATATYPE;
8249                    let cast_array = cast(&array, &cast_type).expect("cast failed");
8250                    let cast_array = cast_array.as_primitive::<$TYPE>();
8251                    assert_eq!(cast_array.data_type(), &cast_type);
8252                    assert_eq!(cast_array, &expected);
8253                }
8254            }};
8255        }
8256
8257        typed_test!(Int16Array, Int16, Int16Type);
8258        typed_test!(Int32Array, Int32, Int32Type);
8259        typed_test!(Int64Array, Int64, Int64Type);
8260
8261        typed_test!(UInt16Array, UInt16, UInt16Type);
8262        typed_test!(UInt32Array, UInt32, UInt32Type);
8263        typed_test!(UInt64Array, UInt64, UInt64Type);
8264
8265        typed_test!(Float16Array, Float16, Float16Type);
8266        typed_test!(Float32Array, Float32, Float32Type);
8267        typed_test!(Float64Array, Float64, Float64Type);
8268
8269        typed_test!(Date32Array, Date32, Date32Type);
8270        typed_test!(Date64Array, Date64, Date64Type);
8271    }
8272
8273    fn cast_from_null_to_other_base(data_type: &DataType, is_complex: bool) {
8274        // Cast from null to data_type
8275        let array = new_null_array(&DataType::Null, 4);
8276        assert_eq!(array.data_type(), &DataType::Null);
8277        let cast_array = cast(&array, data_type).expect("cast failed");
8278        assert_eq!(cast_array.data_type(), data_type);
8279        for i in 0..4 {
8280            if is_complex {
8281                assert!(cast_array.logical_nulls().unwrap().is_null(i));
8282            } else {
8283                assert!(cast_array.is_null(i));
8284            }
8285        }
8286    }
8287
8288    fn cast_from_null_to_other(data_type: &DataType) {
8289        cast_from_null_to_other_base(data_type, false);
8290    }
8291
8292    fn cast_from_null_to_other_complex(data_type: &DataType) {
8293        cast_from_null_to_other_base(data_type, true);
8294    }
8295
8296    #[test]
8297    fn test_cast_null_from_and_to_variable_sized() {
8298        cast_from_null_to_other(&DataType::Utf8);
8299        cast_from_null_to_other(&DataType::LargeUtf8);
8300        cast_from_null_to_other(&DataType::Binary);
8301        cast_from_null_to_other(&DataType::LargeBinary);
8302    }
8303
8304    #[test]
8305    fn test_cast_null_from_and_to_nested_type() {
8306        // Cast null from and to map
8307        let data_type = DataType::Map(
8308            Arc::new(Field::new_struct(
8309                Field::MAP_ENTRIES_FIELD_DEFAULT_NAME,
8310                vec![
8311                    Field::new(Field::MAP_KEY_FIELD_DEFAULT_NAME, DataType::Utf8, false),
8312                    Field::new(Field::MAP_VALUE_FIELD_DEFAULT_NAME, DataType::Int32, true),
8313                ],
8314                false,
8315            )),
8316            false,
8317        );
8318        cast_from_null_to_other(&data_type);
8319
8320        // Cast null from and to list
8321        let data_type = DataType::List(Arc::new(Field::new_list_field(DataType::Int32, true)));
8322        cast_from_null_to_other(&data_type);
8323        let data_type = DataType::LargeList(Arc::new(Field::new_list_field(DataType::Int32, true)));
8324        cast_from_null_to_other(&data_type);
8325        let data_type =
8326            DataType::FixedSizeList(Arc::new(Field::new_list_field(DataType::Int32, true)), 4);
8327        cast_from_null_to_other(&data_type);
8328
8329        // Cast null from and to dictionary
8330        let values = vec![None, None, None, None] as Vec<Option<&str>>;
8331        let array: DictionaryArray<Int8Type> = values.into_iter().collect();
8332        let array = Arc::new(array) as ArrayRef;
8333        let data_type = array.data_type().to_owned();
8334        cast_from_null_to_other(&data_type);
8335
8336        // Cast null from and to struct
8337        let data_type = DataType::Struct(vec![Field::new("data", DataType::Int64, false)].into());
8338        cast_from_null_to_other(&data_type);
8339
8340        let target_type = DataType::ListView(Arc::new(Field::new("item", DataType::Int32, true)));
8341        cast_from_null_to_other(&target_type);
8342
8343        let target_type =
8344            DataType::LargeListView(Arc::new(Field::new("item", DataType::Int32, true)));
8345        cast_from_null_to_other(&target_type);
8346
8347        let fields = UnionFields::from_fields(vec![Field::new("a", DataType::Int64, false)]);
8348        let target_type = DataType::Union(fields, UnionMode::Sparse);
8349        cast_from_null_to_other_complex(&target_type);
8350
8351        let target_type = DataType::RunEndEncoded(
8352            Arc::new(Field::new("item", DataType::Int32, true)),
8353            Arc::new(Field::new("item", DataType::Int32, true)),
8354        );
8355        cast_from_null_to_other_complex(&target_type);
8356    }
8357
8358    #[test]
8359    fn test_cast_utf8_to_date32() {
8360        use chrono::NaiveDate;
8361        let from_ymd = chrono::NaiveDate::from_ymd_opt;
8362        let since = chrono::NaiveDate::signed_duration_since;
8363
8364        let a = StringArray::from(vec![
8365            "2000-01-01",          // valid date with leading 0s
8366            "2000-01-01T12:00:00", // valid datetime, will throw away the time part
8367            "2000-2-2",            // valid date without leading 0s
8368            "2000-00-00",          // invalid month and day
8369            "2000",                // just a year is invalid
8370        ]);
8371        let array = Arc::new(a) as ArrayRef;
8372        let b = cast(&array, &DataType::Date32).unwrap();
8373        let c = b.as_primitive::<Date32Type>();
8374
8375        // test valid inputs
8376        let date_value = since(
8377            NaiveDate::from_ymd_opt(2000, 1, 1).unwrap(),
8378            from_ymd(1970, 1, 1).unwrap(),
8379        )
8380        .num_days() as i32;
8381        assert!(c.is_valid(0)); // "2000-01-01"
8382        assert_eq!(date_value, c.value(0));
8383
8384        assert!(c.is_valid(1)); // "2000-01-01T12:00:00"
8385        assert_eq!(date_value, c.value(1));
8386
8387        let date_value = since(
8388            NaiveDate::from_ymd_opt(2000, 2, 2).unwrap(),
8389            from_ymd(1970, 1, 1).unwrap(),
8390        )
8391        .num_days() as i32;
8392        assert!(c.is_valid(2)); // "2000-2-2"
8393        assert_eq!(date_value, c.value(2));
8394
8395        // test invalid inputs
8396        assert!(!c.is_valid(3)); // "2000-00-00"
8397        assert!(!c.is_valid(4)); // "2000"
8398    }
8399
8400    #[test]
8401    fn test_cast_utf8_to_date64() {
8402        let a = StringArray::from(vec![
8403            "2000-01-01T12:00:00", // date + time valid
8404            "2020-12-15T12:34:56", // date + time valid
8405            "2020-2-2T12:34:56",   // valid date time without leading 0s
8406            "2000-00-00T12:00:00", // invalid month and day
8407            "2000-01-01 12:00:00", // missing the 'T'
8408            "2000-01-01",          // just a date is invalid
8409        ]);
8410        let array = Arc::new(a) as ArrayRef;
8411        let b = cast(&array, &DataType::Date64).unwrap();
8412        let c = b.as_primitive::<Date64Type>();
8413
8414        // test valid inputs
8415        assert!(c.is_valid(0)); // "2000-01-01T12:00:00"
8416        assert_eq!(946728000000, c.value(0));
8417        assert!(c.is_valid(1)); // "2020-12-15T12:34:56"
8418        assert_eq!(1608035696000, c.value(1));
8419        assert!(!c.is_valid(2)); // "2020-2-2T12:34:56"
8420
8421        assert!(!c.is_valid(3)); // "2000-00-00T12:00:00"
8422        assert!(c.is_valid(4)); // "2000-01-01 12:00:00"
8423        assert_eq!(946728000000, c.value(4));
8424        assert!(c.is_valid(5)); // "2000-01-01"
8425        assert_eq!(946684800000, c.value(5));
8426    }
8427
8428    #[test]
8429    fn test_utf8_cast_offsets() {
8430        // test if offset of the array is taken into account during cast
8431        let str_array = StringArray::from(vec!["a", "b", "c"]);
8432        let str_array = str_array.slice(1, 2);
8433
8434        let out = cast(&str_array, &DataType::LargeUtf8).unwrap();
8435
8436        let large_str_array = out.as_any().downcast_ref::<LargeStringArray>().unwrap();
8437        let strs = large_str_array.into_iter().flatten().collect::<Vec<_>>();
8438        assert_eq!(strs, &["b", "c"])
8439    }
8440
8441    #[test]
8442    #[cfg_attr(miri, ignore)] // Takes too long
8443    fn test_cast_f64_to_decimal128() {
8444        // to reproduce https://github.com/apache/arrow-rs/issues/2997
8445
8446        let decimal_type = DataType::Decimal128(18, 2);
8447        let array = Float64Array::from(vec![
8448            Some(0.0699999999),
8449            Some(0.0659999999),
8450            Some(0.0650000000),
8451            Some(0.0649999999),
8452        ]);
8453        let array = Arc::new(array) as ArrayRef;
8454        generate_cast_test_case!(
8455            &array,
8456            Decimal128Array,
8457            &decimal_type,
8458            vec![
8459                Some(7_i128), // round up
8460                Some(7_i128), // round up
8461                Some(7_i128), // round up
8462                Some(6_i128), // round down
8463            ]
8464        );
8465
8466        let decimal_type = DataType::Decimal128(18, 3);
8467        let array = Float64Array::from(vec![
8468            Some(0.0699999999),
8469            Some(0.0659999999),
8470            Some(0.0650000000),
8471            Some(0.0649999999),
8472        ]);
8473        let array = Arc::new(array) as ArrayRef;
8474        generate_cast_test_case!(
8475            &array,
8476            Decimal128Array,
8477            &decimal_type,
8478            vec![
8479                Some(70_i128), // round up
8480                Some(66_i128), // round up
8481                Some(65_i128), // round down
8482                Some(65_i128), // round up
8483            ]
8484        );
8485    }
8486
8487    /// Casts that cannot overflow, whether the source type or the data decides,
8488    /// must match the checked conversion at the extremes, and a value beyond the
8489    /// bound must still become null or an error.
8490    #[test]
8491    fn test_cast_integer_to_decimal_bounds() {
8492        // Every i32 has at most ten digits, so the type decides.
8493        let array = Int32Array::from(vec![Some(i32::MIN), None, Some(-1), Some(i32::MAX)]);
8494        generate_cast_test_case!(
8495            &array,
8496            Decimal128Array,
8497            &DataType::Decimal128(12, 2),
8498            vec![
8499                Some(i32::MIN as i128 * 100),
8500                None,
8501                Some(-100),
8502                Some(i32::MAX as i128 * 100)
8503            ]
8504        );
8505        // An i64 can exceed sixteen digits, so the data decides.
8506        let bound = 9_999_999_999_999_999_i64;
8507        let array = Int64Array::from(vec![Some(-bound), None, Some(bound)]);
8508        generate_cast_test_case!(
8509            &array,
8510            Decimal128Array,
8511            &DataType::Decimal128(18, 2),
8512            vec![Some(-bound as i128 * 100), None, Some(bound as i128 * 100)]
8513        );
8514        // A negative scale divides first, truncating toward zero.
8515        let array = Int32Array::from(vec![Some(-1_234_567), Some(9_999_999)]);
8516        generate_cast_test_case!(
8517            &array,
8518            Decimal32Array,
8519            &DataType::Decimal32(5, -2),
8520            vec![Some(-12_345), Some(99_999)]
8521        );
8522        // One value beyond the bound sends the whole array down the checked path.
8523        let array = Int64Array::from(vec![Some(bound + 1), Some(1)]);
8524        let result = cast(&array, &DataType::Decimal128(18, 2)).unwrap();
8525        let result = result.as_primitive::<Decimal128Type>();
8526        assert!(result.is_null(0));
8527        assert_eq!(result.value(1), 100);
8528        let options = CastOptions {
8529            safe: false,
8530            ..Default::default()
8531        };
8532        assert!(cast_with_options(&array, &DataType::Decimal128(18, 2), &options).is_err());
8533        // A precision beyond the target type is an error even when the values fit it.
8534        let array = Int64Array::from(vec![5_000_000_000]);
8535        for safe in [true, false] {
8536            let options = CastOptions {
8537                safe,
8538                ..Default::default()
8539            };
8540            assert!(cast_with_options(&array, &DataType::Decimal32(10, 0), &options).is_err());
8541        }
8542    }
8543
8544    #[test]
8545    fn test_cast_numeric_to_decimal128_overflow() {
8546        let array = Int64Array::from(vec![i64::MAX]);
8547        let array = Arc::new(array) as ArrayRef;
8548        let casted_array = cast_with_options(
8549            &array,
8550            &DataType::Decimal128(38, 30),
8551            &CastOptions {
8552                safe: true,
8553                format_options: FormatOptions::default(),
8554            },
8555        );
8556        assert!(casted_array.is_ok());
8557        assert!(casted_array.unwrap().is_null(0));
8558
8559        let casted_array = cast_with_options(
8560            &array,
8561            &DataType::Decimal128(38, 30),
8562            &CastOptions {
8563                safe: false,
8564                format_options: FormatOptions::default(),
8565            },
8566        );
8567        assert!(casted_array.is_err());
8568    }
8569
8570    #[test]
8571    fn test_cast_numeric_to_decimal256_overflow() {
8572        let array = Int64Array::from(vec![i64::MAX]);
8573        let array = Arc::new(array) as ArrayRef;
8574        let casted_array = cast_with_options(
8575            &array,
8576            &DataType::Decimal256(76, 76),
8577            &CastOptions {
8578                safe: true,
8579                format_options: FormatOptions::default(),
8580            },
8581        );
8582        assert!(casted_array.is_ok());
8583        assert!(casted_array.unwrap().is_null(0));
8584
8585        let casted_array = cast_with_options(
8586            &array,
8587            &DataType::Decimal256(76, 76),
8588            &CastOptions {
8589                safe: false,
8590                format_options: FormatOptions::default(),
8591            },
8592        );
8593        assert!(casted_array.is_err());
8594    }
8595
8596    #[test]
8597    fn test_cast_integer_to_decimal32_does_not_truncate() {
8598        let array = Int64Array::from(vec![5_000_000_000i64, 10_000_000_000, 42]);
8599        let safe = CastOptions {
8600            safe: true,
8601            format_options: FormatOptions::default(),
8602        };
8603        let unsafe_opts = CastOptions {
8604            safe: false,
8605            format_options: FormatOptions::default(),
8606        };
8607
8608        let result = cast_with_options(&array, &DataType::Decimal32(9, 0), &safe).unwrap();
8609        let result = result.as_primitive::<Decimal32Type>();
8610        assert!(
8611            result.is_null(0),
8612            "5e9 must not wrap to {}",
8613            result.value(0)
8614        );
8615        assert!(result.is_null(1));
8616        assert_eq!(result.value(2), 42);
8617
8618        let err = cast_with_options(&array, &DataType::Decimal32(9, 0), &unsafe_opts)
8619            .unwrap_err()
8620            .to_string();
8621        assert_eq!(
8622            err,
8623            "Cast error: Cannot cast to Decimal32(9, 0). Overflowing on 5000000000"
8624        );
8625
8626        let result = cast_with_options(&array, &DataType::Decimal128(9, 0), &safe).unwrap();
8627        let result = result.as_primitive::<Decimal128Type>();
8628        assert!(result.is_null(0));
8629        assert!(result.is_null(1));
8630        assert_eq!(result.value(2), 42);
8631    }
8632
8633    #[test]
8634    fn test_cast_integer_to_decimal32_scales_before_narrowing() {
8635        let array = Int64Array::from(vec![5_000_000_000i64]);
8636        let safe = CastOptions {
8637            safe: true,
8638            format_options: FormatOptions::default(),
8639        };
8640        let unsafe_opts = CastOptions {
8641            safe: false,
8642            format_options: FormatOptions::default(),
8643        };
8644        let data_type = DataType::Decimal32(9, -1);
8645
8646        let result = cast_with_options(&array, &data_type, &safe).unwrap();
8647        let result = result.as_primitive::<Decimal32Type>();
8648        assert_eq!(result.value(0), 500_000_000);
8649
8650        let result = cast_with_options(&array, &data_type, &unsafe_opts).unwrap();
8651        let result = result.as_primitive::<Decimal32Type>();
8652        assert_eq!(result.value(0), 500_000_000);
8653    }
8654
8655    #[test]
8656    fn test_cast_uint_to_decimal32_does_not_wrap() {
8657        let array = UInt32Array::from(vec![4_000_000_000u32]);
8658        let safe = CastOptions {
8659            safe: true,
8660            format_options: FormatOptions::default(),
8661        };
8662        let unsafe_opts = CastOptions {
8663            safe: false,
8664            format_options: FormatOptions::default(),
8665        };
8666
8667        let result = cast_with_options(&array, &DataType::Decimal32(9, 0), &safe).unwrap();
8668        let result = result.as_primitive::<Decimal32Type>();
8669        assert!(
8670            result.is_null(0),
8671            "u32 4e9 must not wrap to {}",
8672            result.value(0)
8673        );
8674
8675        let err = cast_with_options(&array, &DataType::Decimal32(9, 0), &unsafe_opts)
8676            .unwrap_err()
8677            .to_string();
8678        assert_eq!(
8679            err,
8680            "Cast error: Cannot cast to Decimal32(9, 0). Overflowing on 4000000000"
8681        );
8682
8683        let result = cast_with_options(&array, &DataType::Decimal128(9, 0), &safe).unwrap();
8684        assert!(result.is_null(0));
8685        assert!(cast_with_options(&array, &DataType::Decimal128(9, 0), &unsafe_opts).is_err());
8686    }
8687
8688    #[test]
8689    fn test_cast_uint64_max_to_decimal64_does_not_wrap() {
8690        let array = UInt64Array::from(vec![u64::MAX]);
8691        let unsafe_opts = CastOptions {
8692            safe: false,
8693            format_options: FormatOptions::default(),
8694        };
8695
8696        let err = cast_with_options(&array, &DataType::Decimal64(18, 0), &unsafe_opts)
8697            .unwrap_err()
8698            .to_string();
8699        assert_eq!(
8700            err,
8701            "Cast error: Cannot cast to Decimal64(18, 0). Overflowing on 18446744073709551615"
8702        );
8703
8704        assert!(cast_with_options(&array, &DataType::Decimal128(18, 0), &unsafe_opts).is_err());
8705    }
8706
8707    #[test]
8708    fn test_cast_floating_point_to_decimal128_precision_overflow() {
8709        let array = Float64Array::from(vec![1.1]);
8710        let array = Arc::new(array) as ArrayRef;
8711        let casted_array = cast_with_options(
8712            &array,
8713            &DataType::Decimal128(2, 2),
8714            &CastOptions {
8715                safe: true,
8716                format_options: FormatOptions::default(),
8717            },
8718        );
8719        assert!(casted_array.is_ok());
8720        assert!(casted_array.unwrap().is_null(0));
8721
8722        let casted_array = cast_with_options(
8723            &array,
8724            &DataType::Decimal128(2, 2),
8725            &CastOptions {
8726                safe: false,
8727                format_options: FormatOptions::default(),
8728            },
8729        );
8730        let err = casted_array.unwrap_err().to_string();
8731        let expected_error = "Invalid argument error: 1.10 is too large to store in a Decimal128 of precision 2. Max is 0.99";
8732        assert!(
8733            err.contains(expected_error),
8734            "did not find expected error '{expected_error}' in actual error '{err}'"
8735        );
8736    }
8737
8738    #[test]
8739    #[cfg_attr(miri, ignore)] // Unsupported inline assembly
8740    fn test_cast_float16_to_decimal128_precision_overflow() {
8741        let array = Float16Array::from(vec![f16::from_f32(1.1)]);
8742        let array = Arc::new(array) as ArrayRef;
8743        let casted_array = cast_with_options(
8744            &array,
8745            &DataType::Decimal128(2, 2),
8746            &CastOptions {
8747                safe: true,
8748                format_options: FormatOptions::default(),
8749            },
8750        );
8751        assert!(casted_array.is_ok());
8752        assert!(casted_array.unwrap().is_null(0));
8753
8754        let casted_array = cast_with_options(
8755            &array,
8756            &DataType::Decimal128(2, 2),
8757            &CastOptions {
8758                safe: false,
8759                format_options: FormatOptions::default(),
8760            },
8761        );
8762        let err = casted_array.unwrap_err().to_string();
8763        let expected_error = "Invalid argument error: 1.10 is too large to store in a Decimal128 of precision 2. Max is 0.99";
8764        assert_eq!(err, expected_error);
8765    }
8766
8767    #[test]
8768    #[cfg_attr(miri, ignore)] // Unsupported inline assembly
8769    fn test_cast_float16_to_decimal256_precision_overflow() {
8770        let array = Float16Array::from(vec![f16::from_f32(1.1)]);
8771        let array = Arc::new(array) as ArrayRef;
8772        let casted_array = cast_with_options(
8773            &array,
8774            &DataType::Decimal256(2, 2),
8775            &CastOptions {
8776                safe: true,
8777                format_options: FormatOptions::default(),
8778            },
8779        );
8780        assert!(casted_array.is_ok());
8781        assert!(casted_array.unwrap().is_null(0));
8782
8783        let casted_array = cast_with_options(
8784            &array,
8785            &DataType::Decimal256(2, 2),
8786            &CastOptions {
8787                safe: false,
8788                format_options: FormatOptions::default(),
8789            },
8790        );
8791        let err = casted_array.unwrap_err().to_string();
8792        let expected_error = "Invalid argument error: 1.10 is too large to store in a Decimal256 of precision 2. Max is 0.99";
8793        assert_eq!(err, expected_error);
8794    }
8795
8796    #[test]
8797    #[cfg_attr(miri, ignore)] // Unsupported inline assembly
8798    fn test_cast_float16_to_decimal128_non_finite() {
8799        let array = Float16Array::from(vec![f16::NAN, f16::INFINITY, f16::NEG_INFINITY]);
8800        let array = Arc::new(array) as ArrayRef;
8801        let casted_array = cast_with_options(
8802            &array,
8803            &DataType::Decimal128(38, 2),
8804            &CastOptions {
8805                safe: true,
8806                format_options: FormatOptions::default(),
8807            },
8808        )
8809        .unwrap();
8810
8811        assert!(casted_array.is_null(0));
8812        assert!(casted_array.is_null(1));
8813        assert!(casted_array.is_null(2));
8814
8815        let casted_array = cast_with_options(
8816            &array,
8817            &DataType::Decimal128(38, 2),
8818            &CastOptions {
8819                safe: false,
8820                format_options: FormatOptions::default(),
8821            },
8822        );
8823        let err = casted_array.unwrap_err().to_string();
8824        let expected_error = "Cannot cast to Decimal128(38, 2)";
8825        assert!(
8826            err.contains(expected_error),
8827            "did not find expected error '{expected_error}' in actual error '{err}'"
8828        );
8829    }
8830
8831    #[test]
8832    fn test_cast_floating_point_to_decimal256_precision_overflow() {
8833        let array = Float64Array::from(vec![1.1]);
8834        let array = Arc::new(array) as ArrayRef;
8835        let casted_array = cast_with_options(
8836            &array,
8837            &DataType::Decimal256(2, 2),
8838            &CastOptions {
8839                safe: true,
8840                format_options: FormatOptions::default(),
8841            },
8842        );
8843        assert!(casted_array.is_ok());
8844        assert!(casted_array.unwrap().is_null(0));
8845
8846        let casted_array = cast_with_options(
8847            &array,
8848            &DataType::Decimal256(2, 2),
8849            &CastOptions {
8850                safe: false,
8851                format_options: FormatOptions::default(),
8852            },
8853        );
8854        let err = casted_array.unwrap_err().to_string();
8855        let expected_error = "Invalid argument error: 1.10 is too large to store in a Decimal256 of precision 2. Max is 0.99";
8856        assert_eq!(err, expected_error);
8857    }
8858
8859    #[test]
8860    fn test_cast_floating_point_to_decimal128_overflow() {
8861        let array = Float64Array::from(vec![f64::MAX]);
8862        let array = Arc::new(array) as ArrayRef;
8863        let casted_array = cast_with_options(
8864            &array,
8865            &DataType::Decimal128(38, 30),
8866            &CastOptions {
8867                safe: true,
8868                format_options: FormatOptions::default(),
8869            },
8870        );
8871        assert!(casted_array.is_ok());
8872        assert!(casted_array.unwrap().is_null(0));
8873
8874        let casted_array = cast_with_options(
8875            &array,
8876            &DataType::Decimal128(38, 30),
8877            &CastOptions {
8878                safe: false,
8879                format_options: FormatOptions::default(),
8880            },
8881        );
8882        let err = casted_array.unwrap_err().to_string();
8883        let expected_error = "Cast error: Cannot cast to Decimal128(38, 30)";
8884        assert!(
8885            err.contains(expected_error),
8886            "did not find expected error '{expected_error}' in actual error '{err}'"
8887        );
8888    }
8889
8890    #[test]
8891    fn test_cast_floating_point_to_decimal256_overflow() {
8892        let array = Float64Array::from(vec![f64::MAX]);
8893        let array = Arc::new(array) as ArrayRef;
8894        let casted_array = cast_with_options(
8895            &array,
8896            &DataType::Decimal256(76, 50),
8897            &CastOptions {
8898                safe: true,
8899                format_options: FormatOptions::default(),
8900            },
8901        );
8902        assert!(casted_array.is_ok());
8903        assert!(casted_array.unwrap().is_null(0));
8904
8905        let casted_array = cast_with_options(
8906            &array,
8907            &DataType::Decimal256(76, 50),
8908            &CastOptions {
8909                safe: false,
8910                format_options: FormatOptions::default(),
8911            },
8912        );
8913        let err = casted_array.unwrap_err().to_string();
8914        let expected_error = "Cast error: Cannot cast to Decimal256(76, 50)";
8915        assert!(
8916            err.contains(expected_error),
8917            "did not find expected error '{expected_error}' in actual error '{err}'"
8918        );
8919    }
8920    #[test]
8921    fn test_cast_decimal256_to_f64_no_overflow() {
8922        // Test casting i256::MAX: should produce a large finite positive value
8923        let array = vec![Some(i256::MAX)];
8924        let array = create_decimal256_array(array, 76, 2).unwrap();
8925        let array = Arc::new(array) as ArrayRef;
8926
8927        let result = cast(&array, &DataType::Float64).unwrap();
8928        let result = result.as_primitive::<Float64Type>();
8929        assert!(result.value(0).is_finite());
8930        assert!(result.value(0) > 0.0); // Positive result
8931
8932        // Test casting i256::MIN: should produce a large finite negative value
8933        let array = vec![Some(i256::MIN)];
8934        let array = create_decimal256_array(array, 76, 2).unwrap();
8935        let array = Arc::new(array) as ArrayRef;
8936
8937        let result = cast(&array, &DataType::Float64).unwrap();
8938        let result = result.as_primitive::<Float64Type>();
8939        assert!(result.value(0).is_finite());
8940        assert!(result.value(0) < 0.0); // Negative result
8941    }
8942
8943    #[test]
8944    fn test_cast_decimal256_negative_scale_metadata() {
8945        let input = Decimal256Array::from(vec![
8946            Some(i256::ZERO),
8947            Some(i256::ONE),
8948            Some(i256::MINUS_ONE),
8949            None,
8950        ])
8951        .with_precision_and_scale(76, -51)
8952        .unwrap();
8953        let value = i256::from_i128(10).pow_wrapping(51);
8954        let expected =
8955            Decimal256Array::from(vec![Some(i256::ZERO), Some(value), Some(-value), None])
8956                .with_precision_and_scale(76, 0)
8957                .unwrap();
8958        let options = CastOptions {
8959            safe: false,
8960            ..Default::default()
8961        };
8962        let output_type = DataType::Decimal256(76, 0);
8963        let result = cast(&input, &output_type).unwrap();
8964        assert_eq!(result.as_primitive::<Decimal256Type>(), &expected);
8965        let result = cast_with_options(&input, &output_type, &options).unwrap();
8966        assert_eq!(result.as_primitive::<Decimal256Type>(), &expected);
8967
8968        // The precision plus scale increase crosses i8::MAX at -52.
8969        let input = input.with_precision_and_scale(76, -52).unwrap();
8970        let value = i256::from_i128(10).pow_wrapping(52);
8971        let expected =
8972            Decimal256Array::from(vec![Some(i256::ZERO), Some(value), Some(-value), None])
8973                .with_precision_and_scale(76, 0)
8974                .unwrap();
8975        let result = cast(&input, &output_type).unwrap();
8976        assert_eq!(result.as_primitive::<Decimal256Type>(), &expected);
8977        let result = cast_with_options(&input, &output_type, &options).unwrap();
8978        assert_eq!(result.as_primitive::<Decimal256Type>(), &expected);
8979    }
8980
8981    #[test]
8982    fn test_cast_decimal256_negative_scale_precision_overflow() {
8983        let input = Decimal256Array::from(vec![Some(i256::ZERO), Some(i256::ONE), None])
8984            .with_precision_and_scale(76, -76)
8985            .unwrap();
8986        let output_type = DataType::Decimal256(76, 0);
8987        let expected = Decimal256Array::from(vec![Some(i256::ZERO), None, None])
8988            .with_precision_and_scale(76, 0)
8989            .unwrap();
8990        let result = cast(&input, &output_type).unwrap();
8991        assert_eq!(result.as_primitive::<Decimal256Type>(), &expected);
8992
8993        let options = CastOptions {
8994            safe: false,
8995            ..Default::default()
8996        };
8997        let error = cast_with_options(&input, &output_type, &options).unwrap_err();
8998        let value = i256::from_i128(10).pow_wrapping(76);
8999        assert_eq!(
9000            error.to_string(),
9001            format!(
9002                "Invalid argument error: {value} is too large to store in a Decimal256 of precision 76. Max is {}",
9003                value - i256::ONE
9004            )
9005        );
9006    }
9007
9008    #[test]
9009    fn test_cast_decimal256_negative_scale_native_overflow() {
9010        let input = Decimal256Array::from(vec![Some(i256::from_i128(6)), None])
9011            .with_precision_and_scale(76, -76)
9012            .unwrap();
9013        let output_type = DataType::Decimal256(76, 0);
9014        let expected = Decimal256Array::from(vec![None, None])
9015            .with_precision_and_scale(76, 0)
9016            .unwrap();
9017        let result = cast(&input, &output_type).unwrap();
9018        assert_eq!(result.as_primitive::<Decimal256Type>(), &expected);
9019
9020        let options = CastOptions {
9021            safe: false,
9022            ..Default::default()
9023        };
9024        let error = cast_with_options(&input, &output_type, &options).unwrap_err();
9025        assert_eq!(
9026            error.to_string(),
9027            "Cast error: Cannot cast to Decimal256(76, 0). Overflowing on 6"
9028        );
9029    }
9030
9031    #[test]
9032    fn test_cast_decimal256_extreme_scale_difference() {
9033        let input = Decimal256Array::from(vec![Some(i256::ONE), Some(i256::MINUS_ONE), None])
9034            .with_precision_and_scale(76, i8::MIN)
9035            .unwrap();
9036        for safe in [true, false] {
9037            let options = CastOptions {
9038                safe,
9039                ..Default::default()
9040            };
9041            let error =
9042                cast_with_options(&input, &DataType::Decimal256(76, 76), &options).unwrap_err();
9043            assert_eq!(
9044                error.to_string(),
9045                "Cast error: Cannot cast to Decimal256(76, 76). Value overflows for output scale"
9046            );
9047        }
9048
9049        let input = input.with_precision_and_scale(76, 76).unwrap();
9050        let expected = Decimal256Array::from(vec![Some(i256::ZERO), Some(i256::ZERO), None])
9051            .with_precision_and_scale(76, i8::MIN)
9052            .unwrap();
9053        for safe in [true, false] {
9054            let options = CastOptions {
9055                safe,
9056                ..Default::default()
9057            };
9058            let result =
9059                cast_with_options(&input, &DataType::Decimal256(76, i8::MIN), &options).unwrap();
9060            assert_eq!(result.as_primitive::<Decimal256Type>(), &expected);
9061        }
9062    }
9063
9064    #[test]
9065    fn test_cast_decimal128_to_decimal128_negative_scale() {
9066        let input_type = DataType::Decimal128(20, 0);
9067        let output_type = DataType::Decimal128(20, -1);
9068        assert!(can_cast_types(&input_type, &output_type));
9069        let array = vec![Some(1123450), Some(2123455), Some(3123456), None];
9070        let input_decimal_array = create_decimal128_array(array, 20, 0).unwrap();
9071        let array = Arc::new(input_decimal_array) as ArrayRef;
9072        generate_cast_test_case!(
9073            &array,
9074            Decimal128Array,
9075            &output_type,
9076            vec![
9077                Some(112345_i128),
9078                Some(212346_i128),
9079                Some(312346_i128),
9080                None
9081            ]
9082        );
9083
9084        let casted_array = cast(&array, &output_type).unwrap();
9085        let decimal_arr = casted_array.as_primitive::<Decimal128Type>();
9086
9087        assert_eq!("1123450", decimal_arr.value_as_string(0));
9088        assert_eq!("2123460", decimal_arr.value_as_string(1));
9089        assert_eq!("3123460", decimal_arr.value_as_string(2));
9090    }
9091
9092    #[test]
9093    fn decimal128_min_max_to_f64() {
9094        // Ensure Decimal128 i128::MIN/MAX round-trip cast
9095        let min128 = i128::MIN;
9096        let max128 = i128::MAX;
9097        assert_eq!(min128 as f64, min128 as f64);
9098        assert_eq!(max128 as f64, max128 as f64);
9099    }
9100
9101    #[test]
9102    fn test_cast_numeric_to_decimal128_negative() {
9103        let decimal_type = DataType::Decimal128(38, -1);
9104        let array = Arc::new(Int32Array::from(vec![
9105            Some(1123456),
9106            Some(2123456),
9107            Some(3123456),
9108        ])) as ArrayRef;
9109
9110        let casted_array = cast(&array, &decimal_type).unwrap();
9111        let decimal_arr = casted_array.as_primitive::<Decimal128Type>();
9112
9113        assert_eq!("1123450", decimal_arr.value_as_string(0));
9114        assert_eq!("2123450", decimal_arr.value_as_string(1));
9115        assert_eq!("3123450", decimal_arr.value_as_string(2));
9116
9117        let array = Arc::new(Float32Array::from(vec![
9118            Some(1123.456),
9119            Some(2123.456),
9120            Some(3123.456),
9121        ])) as ArrayRef;
9122
9123        let casted_array = cast(&array, &decimal_type).unwrap();
9124        let decimal_arr = casted_array.as_primitive::<Decimal128Type>();
9125
9126        assert_eq!("1120", decimal_arr.value_as_string(0));
9127        assert_eq!("2120", decimal_arr.value_as_string(1));
9128        assert_eq!("3120", decimal_arr.value_as_string(2));
9129    }
9130
9131    #[test]
9132    fn test_cast_decimal128_to_decimal128_negative() {
9133        let input_type = DataType::Decimal128(10, -1);
9134        let output_type = DataType::Decimal128(10, -2);
9135        assert!(can_cast_types(&input_type, &output_type));
9136        let array = vec![Some(123)];
9137        let input_decimal_array = create_decimal128_array(array, 10, -1).unwrap();
9138        let array = Arc::new(input_decimal_array) as ArrayRef;
9139        generate_cast_test_case!(&array, Decimal128Array, &output_type, vec![Some(12_i128),]);
9140
9141        let casted_array = cast(&array, &output_type).unwrap();
9142        let decimal_arr = casted_array.as_primitive::<Decimal128Type>();
9143
9144        assert_eq!("1200", decimal_arr.value_as_string(0));
9145
9146        let array = vec![Some(125)];
9147        let input_decimal_array = create_decimal128_array(array, 10, -1).unwrap();
9148        let array = Arc::new(input_decimal_array) as ArrayRef;
9149        generate_cast_test_case!(&array, Decimal128Array, &output_type, vec![Some(13_i128),]);
9150
9151        let casted_array = cast(&array, &output_type).unwrap();
9152        let decimal_arr = casted_array.as_primitive::<Decimal128Type>();
9153
9154        assert_eq!("1300", decimal_arr.value_as_string(0));
9155    }
9156
9157    #[test]
9158    fn test_cast_decimal128_to_decimal256_negative() {
9159        let input_type = DataType::Decimal128(10, 3);
9160        let output_type = DataType::Decimal256(10, 5);
9161        assert!(can_cast_types(&input_type, &output_type));
9162        let array = vec![Some(123456), Some(-123456)];
9163        let input_decimal_array = create_decimal128_array(array, 10, 3).unwrap();
9164        let array = Arc::new(input_decimal_array) as ArrayRef;
9165
9166        let hundred = i256::from_i128(100);
9167        generate_cast_test_case!(
9168            &array,
9169            Decimal256Array,
9170            &output_type,
9171            vec![
9172                Some(i256::from_i128(123456).mul_wrapping(hundred)),
9173                Some(i256::from_i128(-123456).mul_wrapping(hundred))
9174            ]
9175        );
9176    }
9177
9178    #[test]
9179    fn test_parse_decimal_and_format() {
9180        assert_eq!(
9181            Decimal128Type::format_decimal(
9182                parse_decimal::<Decimal128Type>("123.45", 38, 2).unwrap(),
9183                38,
9184                2,
9185            ),
9186            "123.45"
9187        );
9188        assert_eq!(
9189            Decimal128Type::format_decimal(
9190                parse_decimal::<Decimal128Type>("12345", 38, 2).unwrap(),
9191                38,
9192                2,
9193            ),
9194            "12345.00"
9195        );
9196        assert_eq!(
9197            Decimal128Type::format_decimal(
9198                parse_decimal::<Decimal128Type>("0.12345", 38, 2).unwrap(),
9199                38,
9200                2,
9201            ),
9202            "0.12"
9203        );
9204        assert_eq!(
9205            Decimal128Type::format_decimal(
9206                parse_decimal::<Decimal128Type>(".12345", 38, 2).unwrap(),
9207                38,
9208                2,
9209            ),
9210            "0.12"
9211        );
9212        assert_eq!(
9213            Decimal128Type::format_decimal(
9214                parse_decimal::<Decimal128Type>(".1265", 38, 2).unwrap(),
9215                38,
9216                2,
9217            ),
9218            "0.13"
9219        );
9220        assert_eq!(
9221            Decimal128Type::format_decimal(
9222                parse_decimal::<Decimal128Type>(".1265", 38, 2).unwrap(),
9223                38,
9224                2,
9225            ),
9226            "0.13"
9227        );
9228
9229        assert_eq!(
9230            Decimal256Type::format_decimal(
9231                parse_decimal::<Decimal256Type>("123.45", 76, 3).unwrap(),
9232                38,
9233                3,
9234            ),
9235            "123.450"
9236        );
9237        assert_eq!(
9238            Decimal256Type::format_decimal(
9239                parse_decimal::<Decimal256Type>("12345", 76, 3).unwrap(),
9240                38,
9241                3,
9242            ),
9243            "12345.000"
9244        );
9245        assert_eq!(
9246            Decimal256Type::format_decimal(
9247                parse_decimal::<Decimal256Type>("0.12345", 76, 3).unwrap(),
9248                38,
9249                3,
9250            ),
9251            "0.123"
9252        );
9253        assert_eq!(
9254            Decimal256Type::format_decimal(
9255                parse_decimal::<Decimal256Type>(".12345", 76, 3).unwrap(),
9256                38,
9257                3,
9258            ),
9259            "0.123"
9260        );
9261        assert_eq!(
9262            Decimal256Type::format_decimal(
9263                parse_decimal::<Decimal256Type>(".1265", 76, 3).unwrap(),
9264                38,
9265                3,
9266            ),
9267            "0.127"
9268        );
9269    }
9270
9271    fn test_cast_string_to_decimal(array: ArrayRef) {
9272        // Decimal128
9273        let output_type = DataType::Decimal128(38, 2);
9274        assert!(can_cast_types(array.data_type(), &output_type));
9275
9276        let casted_array = cast(&array, &output_type).unwrap();
9277        let decimal_arr = casted_array.as_primitive::<Decimal128Type>();
9278
9279        assert_eq!("123.45", decimal_arr.value_as_string(0));
9280        assert_eq!("1.23", decimal_arr.value_as_string(1));
9281        assert_eq!("0.12", decimal_arr.value_as_string(2));
9282        assert_eq!("0.13", decimal_arr.value_as_string(3));
9283        assert_eq!("1.26", decimal_arr.value_as_string(4));
9284        assert_eq!("12345.00", decimal_arr.value_as_string(5));
9285        assert_eq!("12345.00", decimal_arr.value_as_string(6));
9286        assert_eq!("0.12", decimal_arr.value_as_string(7));
9287        assert_eq!("12.23", decimal_arr.value_as_string(8));
9288        assert!(decimal_arr.is_null(9));
9289        assert!(decimal_arr.is_null(10));
9290        assert!(decimal_arr.is_null(11));
9291        assert!(decimal_arr.is_null(12));
9292        assert_eq!("-1.23", decimal_arr.value_as_string(13));
9293        assert_eq!("-1.24", decimal_arr.value_as_string(14));
9294        assert_eq!("0.00", decimal_arr.value_as_string(15));
9295        assert_eq!("-123.00", decimal_arr.value_as_string(16));
9296        assert_eq!("-123.23", decimal_arr.value_as_string(17));
9297        assert_eq!("-0.12", decimal_arr.value_as_string(18));
9298        assert_eq!("1.23", decimal_arr.value_as_string(19));
9299        assert_eq!("1.24", decimal_arr.value_as_string(20));
9300        assert_eq!("0.00", decimal_arr.value_as_string(21));
9301        assert_eq!("123.00", decimal_arr.value_as_string(22));
9302        assert_eq!("123.23", decimal_arr.value_as_string(23));
9303        assert_eq!("0.12", decimal_arr.value_as_string(24));
9304        assert!(decimal_arr.is_null(25));
9305        assert!(decimal_arr.is_null(26));
9306        assert!(decimal_arr.is_null(27));
9307        assert_eq!("0.00", decimal_arr.value_as_string(28));
9308        assert_eq!("0.00", decimal_arr.value_as_string(29));
9309        assert_eq!("12345.00", decimal_arr.value_as_string(30));
9310        assert_eq!(decimal_arr.len(), 31);
9311
9312        // Decimal256
9313        let output_type = DataType::Decimal256(76, 3);
9314        assert!(can_cast_types(array.data_type(), &output_type));
9315
9316        let casted_array = cast(&array, &output_type).unwrap();
9317        let decimal_arr = casted_array.as_primitive::<Decimal256Type>();
9318
9319        assert_eq!("123.450", decimal_arr.value_as_string(0));
9320        assert_eq!("1.235", decimal_arr.value_as_string(1));
9321        assert_eq!("0.123", decimal_arr.value_as_string(2));
9322        assert_eq!("0.127", decimal_arr.value_as_string(3));
9323        assert_eq!("1.263", decimal_arr.value_as_string(4));
9324        assert_eq!("12345.000", decimal_arr.value_as_string(5));
9325        assert_eq!("12345.000", decimal_arr.value_as_string(6));
9326        assert_eq!("0.123", decimal_arr.value_as_string(7));
9327        assert_eq!("12.234", decimal_arr.value_as_string(8));
9328        assert!(decimal_arr.is_null(9));
9329        assert!(decimal_arr.is_null(10));
9330        assert!(decimal_arr.is_null(11));
9331        assert!(decimal_arr.is_null(12));
9332        assert_eq!("-1.235", decimal_arr.value_as_string(13));
9333        assert_eq!("-1.236", decimal_arr.value_as_string(14));
9334        assert_eq!("0.000", decimal_arr.value_as_string(15));
9335        assert_eq!("-123.000", decimal_arr.value_as_string(16));
9336        assert_eq!("-123.234", decimal_arr.value_as_string(17));
9337        assert_eq!("-0.123", decimal_arr.value_as_string(18));
9338        assert_eq!("1.235", decimal_arr.value_as_string(19));
9339        assert_eq!("1.236", decimal_arr.value_as_string(20));
9340        assert_eq!("0.000", decimal_arr.value_as_string(21));
9341        assert_eq!("123.000", decimal_arr.value_as_string(22));
9342        assert_eq!("123.234", decimal_arr.value_as_string(23));
9343        assert_eq!("0.123", decimal_arr.value_as_string(24));
9344        assert!(decimal_arr.is_null(25));
9345        assert!(decimal_arr.is_null(26));
9346        assert!(decimal_arr.is_null(27));
9347        assert_eq!("0.000", decimal_arr.value_as_string(28));
9348        assert_eq!("0.000", decimal_arr.value_as_string(29));
9349        assert_eq!("12345.000", decimal_arr.value_as_string(30));
9350        assert_eq!(decimal_arr.len(), 31);
9351    }
9352
9353    #[test]
9354    fn test_cast_utf8_to_decimal() {
9355        let str_array = StringArray::from(vec![
9356            Some("123.45"),
9357            Some("1.2345"),
9358            Some("0.12345"),
9359            Some("0.1267"),
9360            Some("1.263"),
9361            Some("12345.0"),
9362            Some("12345"),
9363            Some("000.123"),
9364            Some("12.234000"),
9365            None,
9366            Some(""),
9367            Some(" "),
9368            None,
9369            Some("-1.23499999"),
9370            Some("-1.23599999"),
9371            Some("-0.00001"),
9372            Some("-123"),
9373            Some("-123.234000"),
9374            Some("-000.123"),
9375            Some("+1.23499999"),
9376            Some("+1.23599999"),
9377            Some("+0.00001"),
9378            Some("+123"),
9379            Some("+123.234000"),
9380            Some("+000.123"),
9381            Some("1.-23499999"),
9382            Some("-1.-23499999"),
9383            Some("--1.23499999"),
9384            Some("0"),
9385            Some("000.000"),
9386            Some("0000000000000000012345.000"),
9387        ]);
9388        let array = Arc::new(str_array) as ArrayRef;
9389
9390        test_cast_string_to_decimal(array);
9391
9392        let test_cases = [
9393            (None, None),
9394            (Some(""), None),
9395            (Some("   "), None),
9396            (Some("0"), Some("0")),
9397            (Some("000.000"), Some("0")),
9398            (Some("12345"), Some("12345")),
9399            (Some("000000000000000000000000000012345"), Some("12345")),
9400            (Some("-123"), Some("-123")),
9401            (Some("+123"), Some("123")),
9402        ];
9403        let inputs = test_cases.iter().map(|entry| entry.0).collect::<Vec<_>>();
9404        let expected = test_cases.iter().map(|entry| entry.1).collect::<Vec<_>>();
9405
9406        let array = Arc::new(StringArray::from(inputs)) as ArrayRef;
9407        test_cast_string_to_decimal_scale_zero(array, &expected);
9408    }
9409
9410    #[test]
9411    fn test_cast_large_utf8_to_decimal() {
9412        let str_array = LargeStringArray::from(vec![
9413            Some("123.45"),
9414            Some("1.2345"),
9415            Some("0.12345"),
9416            Some("0.1267"),
9417            Some("1.263"),
9418            Some("12345.0"),
9419            Some("12345"),
9420            Some("000.123"),
9421            Some("12.234000"),
9422            None,
9423            Some(""),
9424            Some(" "),
9425            None,
9426            Some("-1.23499999"),
9427            Some("-1.23599999"),
9428            Some("-0.00001"),
9429            Some("-123"),
9430            Some("-123.234000"),
9431            Some("-000.123"),
9432            Some("+1.23499999"),
9433            Some("+1.23599999"),
9434            Some("+0.00001"),
9435            Some("+123"),
9436            Some("+123.234000"),
9437            Some("+000.123"),
9438            Some("1.-23499999"),
9439            Some("-1.-23499999"),
9440            Some("--1.23499999"),
9441            Some("0"),
9442            Some("000.000"),
9443            Some("0000000000000000012345.000"),
9444        ]);
9445        let array = Arc::new(str_array) as ArrayRef;
9446
9447        test_cast_string_to_decimal(array);
9448
9449        let test_cases = [
9450            (None, None),
9451            (Some(""), None),
9452            (Some("   "), None),
9453            (Some("0"), Some("0")),
9454            (Some("000.000"), Some("0")),
9455            (Some("12345"), Some("12345")),
9456            (Some("000000000000000000000000000012345"), Some("12345")),
9457            (Some("-123"), Some("-123")),
9458            (Some("+123"), Some("123")),
9459        ];
9460        let inputs = test_cases.iter().map(|entry| entry.0).collect::<Vec<_>>();
9461        let expected = test_cases.iter().map(|entry| entry.1).collect::<Vec<_>>();
9462
9463        let array = Arc::new(LargeStringArray::from(inputs)) as ArrayRef;
9464        test_cast_string_to_decimal_scale_zero(array, &expected);
9465    }
9466
9467    fn test_cast_string_to_decimal_scale_zero(
9468        array: ArrayRef,
9469        expected_as_string: &[Option<&str>],
9470    ) {
9471        // Decimal128
9472        let output_type = DataType::Decimal128(38, 0);
9473        assert!(can_cast_types(array.data_type(), &output_type));
9474        let casted_array = cast(&array, &output_type).unwrap();
9475        let decimal_arr = casted_array.as_primitive::<Decimal128Type>();
9476        assert_decimal_array_contents(decimal_arr, expected_as_string);
9477
9478        // Decimal256
9479        let output_type = DataType::Decimal256(76, 0);
9480        assert!(can_cast_types(array.data_type(), &output_type));
9481        let casted_array = cast(&array, &output_type).unwrap();
9482        let decimal_arr = casted_array.as_primitive::<Decimal256Type>();
9483        assert_decimal_array_contents(decimal_arr, expected_as_string);
9484    }
9485
9486    fn assert_decimal_array_contents<T>(
9487        array: &PrimitiveArray<T>,
9488        expected_as_string: &[Option<&str>],
9489    ) where
9490        T: DecimalType + ArrowPrimitiveType,
9491    {
9492        assert_eq!(array.len(), expected_as_string.len());
9493        for (i, expected) in expected_as_string.iter().enumerate() {
9494            let actual = if array.is_null(i) {
9495                None
9496            } else {
9497                Some(array.value_as_string(i))
9498            };
9499            let actual = actual.as_ref().map(|s| s.as_ref());
9500            assert_eq!(*expected, actual, "Expected at position {i}");
9501        }
9502    }
9503
9504    #[test]
9505    fn test_cast_invalid_utf8_to_decimal() {
9506        let str_array = StringArray::from(vec!["4.4.5", ". 0.123"]);
9507        let array = Arc::new(str_array) as ArrayRef;
9508
9509        // Safe cast
9510        let output_type = DataType::Decimal128(38, 2);
9511        let casted_array = cast(&array, &output_type).unwrap();
9512        assert!(casted_array.is_null(0));
9513        assert!(casted_array.is_null(1));
9514
9515        let output_type = DataType::Decimal256(76, 2);
9516        let casted_array = cast(&array, &output_type).unwrap();
9517        assert!(casted_array.is_null(0));
9518        assert!(casted_array.is_null(1));
9519
9520        // Non-safe cast
9521        let output_type = DataType::Decimal128(38, 2);
9522        let str_array = StringArray::from(vec!["4.4.5"]);
9523        let array = Arc::new(str_array) as ArrayRef;
9524        let option = CastOptions {
9525            safe: false,
9526            format_options: FormatOptions::default(),
9527        };
9528        let casted_err = cast_with_options(&array, &output_type, &option).unwrap_err();
9529        assert!(
9530            casted_err
9531                .to_string()
9532                .contains("Cannot cast string '4.4.5' to value of Decimal128(38, 2) type")
9533        );
9534
9535        let str_array = StringArray::from(vec![". 0.123"]);
9536        let array = Arc::new(str_array) as ArrayRef;
9537        let casted_err = cast_with_options(&array, &output_type, &option).unwrap_err();
9538        assert!(
9539            casted_err
9540                .to_string()
9541                .contains("Cannot cast string '. 0.123' to value of Decimal128(38, 2) type")
9542        );
9543
9544        let str_array = StringArray::from(vec![""]);
9545        let array = Arc::new(str_array) as ArrayRef;
9546        let casted_err = cast_with_options(&array, &output_type, &option).unwrap_err();
9547        assert!(
9548            casted_err
9549                .to_string()
9550                .contains("Cannot cast string '' to value of Decimal128(38, 2) type")
9551        );
9552    }
9553
9554    fn test_cast_string_to_decimal128_overflow(overflow_array: ArrayRef) {
9555        let output_type = DataType::Decimal128(38, 2);
9556        let casted_array = cast(&overflow_array, &output_type).unwrap();
9557        let decimal_arr = casted_array.as_primitive::<Decimal128Type>();
9558
9559        assert!(decimal_arr.is_null(0));
9560        assert!(decimal_arr.is_null(1));
9561        assert!(decimal_arr.is_null(2));
9562        assert_eq!(
9563            "999999999999999999999999999999999999.99",
9564            decimal_arr.value_as_string(3)
9565        );
9566        assert_eq!(
9567            "100000000000000000000000000000000000.00",
9568            decimal_arr.value_as_string(4)
9569        );
9570    }
9571
9572    #[test]
9573    fn test_cast_string_to_decimal128_precision_overflow() {
9574        let array = StringArray::from(vec!["1000".to_string()]);
9575        let array = Arc::new(array) as ArrayRef;
9576        let casted_array = cast_with_options(
9577            &array,
9578            &DataType::Decimal128(10, 8),
9579            &CastOptions {
9580                safe: true,
9581                format_options: FormatOptions::default(),
9582            },
9583        );
9584        assert!(casted_array.is_ok());
9585        assert!(casted_array.unwrap().is_null(0));
9586
9587        let err = cast_with_options(
9588            &array,
9589            &DataType::Decimal128(10, 8),
9590            &CastOptions {
9591                safe: false,
9592                format_options: FormatOptions::default(),
9593            },
9594        );
9595        assert_eq!(
9596            "Cast error: Cannot cast string '1000' to value of Decimal128(10, 8) type: value does not fit",
9597            err.unwrap_err().to_string()
9598        );
9599    }
9600
9601    #[test]
9602    fn test_cast_utf8_to_decimal128_overflow() {
9603        let overflow_str_array = StringArray::from(vec![
9604            i128::MAX.to_string(),
9605            i128::MIN.to_string(),
9606            "99999999999999999999999999999999999999".to_string(),
9607            "999999999999999999999999999999999999.99".to_string(),
9608            "99999999999999999999999999999999999.999".to_string(),
9609        ]);
9610        let overflow_array = Arc::new(overflow_str_array) as ArrayRef;
9611
9612        test_cast_string_to_decimal128_overflow(overflow_array);
9613    }
9614
9615    #[test]
9616    fn test_cast_large_utf8_to_decimal128_overflow() {
9617        let overflow_str_array = LargeStringArray::from(vec![
9618            i128::MAX.to_string(),
9619            i128::MIN.to_string(),
9620            "99999999999999999999999999999999999999".to_string(),
9621            "999999999999999999999999999999999999.99".to_string(),
9622            "99999999999999999999999999999999999.999".to_string(),
9623        ]);
9624        let overflow_array = Arc::new(overflow_str_array) as ArrayRef;
9625
9626        test_cast_string_to_decimal128_overflow(overflow_array);
9627    }
9628
9629    fn test_cast_string_to_decimal256_overflow(overflow_array: ArrayRef) {
9630        let output_type = DataType::Decimal256(76, 2);
9631        let casted_array = cast(&overflow_array, &output_type).unwrap();
9632        let decimal_arr = casted_array.as_primitive::<Decimal256Type>();
9633
9634        assert_eq!(
9635            "170141183460469231731687303715884105727.00",
9636            decimal_arr.value_as_string(0)
9637        );
9638        assert_eq!(
9639            "-170141183460469231731687303715884105728.00",
9640            decimal_arr.value_as_string(1)
9641        );
9642        assert_eq!(
9643            "99999999999999999999999999999999999999.00",
9644            decimal_arr.value_as_string(2)
9645        );
9646        assert_eq!(
9647            "999999999999999999999999999999999999.99",
9648            decimal_arr.value_as_string(3)
9649        );
9650        assert_eq!(
9651            "100000000000000000000000000000000000.00",
9652            decimal_arr.value_as_string(4)
9653        );
9654        assert!(decimal_arr.is_null(5));
9655        assert!(decimal_arr.is_null(6));
9656    }
9657
9658    #[test]
9659    fn test_cast_string_to_decimal256_precision_overflow() {
9660        let array = StringArray::from(vec!["1000".to_string()]);
9661        let array = Arc::new(array) as ArrayRef;
9662        let casted_array = cast_with_options(
9663            &array,
9664            &DataType::Decimal256(10, 8),
9665            &CastOptions {
9666                safe: true,
9667                format_options: FormatOptions::default(),
9668            },
9669        );
9670        assert!(casted_array.is_ok());
9671        assert!(casted_array.unwrap().is_null(0));
9672
9673        let err = cast_with_options(
9674            &array,
9675            &DataType::Decimal256(10, 8),
9676            &CastOptions {
9677                safe: false,
9678                format_options: FormatOptions::default(),
9679            },
9680        );
9681        assert_eq!(
9682            "Cast error: Cannot cast string '1000' to value of Decimal256(10, 8) type: value does not fit",
9683            err.unwrap_err().to_string()
9684        );
9685    }
9686
9687    #[test]
9688    fn test_cast_utf8_to_decimal256_overflow() {
9689        let overflow_str_array = StringArray::from(vec![
9690            i128::MAX.to_string(),
9691            i128::MIN.to_string(),
9692            "99999999999999999999999999999999999999".to_string(),
9693            "999999999999999999999999999999999999.99".to_string(),
9694            "99999999999999999999999999999999999.999".to_string(),
9695            i256::MAX.to_string(),
9696            i256::MIN.to_string(),
9697        ]);
9698        let overflow_array = Arc::new(overflow_str_array) as ArrayRef;
9699
9700        test_cast_string_to_decimal256_overflow(overflow_array);
9701    }
9702
9703    #[test]
9704    fn test_cast_large_utf8_to_decimal256_overflow() {
9705        let overflow_str_array = LargeStringArray::from(vec![
9706            i128::MAX.to_string(),
9707            i128::MIN.to_string(),
9708            "99999999999999999999999999999999999999".to_string(),
9709            "999999999999999999999999999999999999.99".to_string(),
9710            "99999999999999999999999999999999999.999".to_string(),
9711            i256::MAX.to_string(),
9712            i256::MIN.to_string(),
9713        ]);
9714        let overflow_array = Arc::new(overflow_str_array) as ArrayRef;
9715
9716        test_cast_string_to_decimal256_overflow(overflow_array);
9717    }
9718
9719    #[test]
9720    fn test_cast_outside_supported_range_for_nanoseconds() {
9721        const EXPECTED_ERROR_MESSAGE: &str = "The dates that can be represented as nanoseconds have to be between 1677-09-21T00:12:44.0 and 2262-04-11T23:47:16.854775804";
9722
9723        let array = StringArray::from(vec![Some("1650-01-01 01:01:01.000001")]);
9724
9725        let cast_options = CastOptions {
9726            safe: false,
9727            format_options: FormatOptions::default(),
9728        };
9729
9730        let result =
9731            cast_string_to_timestamp::<i32, TimestampNanosecondType>(&array, None, &cast_options);
9732
9733        let err = result.unwrap_err();
9734        assert_eq!(
9735            err.to_string(),
9736            format!(
9737                "Cast error: Overflow converting {} to Nanosecond. {}",
9738                array.value(0),
9739                EXPECTED_ERROR_MESSAGE
9740            )
9741        );
9742    }
9743
9744    #[test]
9745    fn test_cast_date32_to_timestamp() {
9746        let a = Date32Array::from(vec![Some(18628), Some(18993), None]); // 2021-1-1, 2022-1-1
9747        let array = Arc::new(a) as ArrayRef;
9748        let b = cast(&array, &DataType::Timestamp(TimeUnit::Second, None)).unwrap();
9749        let c = b.as_primitive::<TimestampSecondType>();
9750        assert_eq!(1609459200, c.value(0));
9751        assert_eq!(1640995200, c.value(1));
9752        assert!(c.is_null(2));
9753    }
9754
9755    #[test]
9756    fn test_cast_date32_to_timestamp_ms() {
9757        let a = Date32Array::from(vec![Some(18628), Some(18993), None]); // 2021-1-1, 2022-1-1
9758        let array = Arc::new(a) as ArrayRef;
9759        let b = cast(&array, &DataType::Timestamp(TimeUnit::Millisecond, None)).unwrap();
9760        let c = b
9761            .as_any()
9762            .downcast_ref::<TimestampMillisecondArray>()
9763            .unwrap();
9764        assert_eq!(1609459200000, c.value(0));
9765        assert_eq!(1640995200000, c.value(1));
9766        assert!(c.is_null(2));
9767    }
9768
9769    #[test]
9770    fn test_cast_date32_to_timestamp_us() {
9771        let a = Date32Array::from(vec![Some(18628), Some(18993), None]); // 2021-1-1, 2022-1-1
9772        let array = Arc::new(a) as ArrayRef;
9773        let b = cast(&array, &DataType::Timestamp(TimeUnit::Microsecond, None)).unwrap();
9774        let c = b
9775            .as_any()
9776            .downcast_ref::<TimestampMicrosecondArray>()
9777            .unwrap();
9778        assert_eq!(1609459200000000, c.value(0));
9779        assert_eq!(1640995200000000, c.value(1));
9780        assert!(c.is_null(2));
9781    }
9782
9783    #[test]
9784    fn test_cast_date32_to_timestamp_ns() {
9785        let a = Date32Array::from(vec![Some(18628), Some(18993), None]); // 2021-1-1, 2022-1-1
9786        let array = Arc::new(a) as ArrayRef;
9787        let b = cast(&array, &DataType::Timestamp(TimeUnit::Nanosecond, None)).unwrap();
9788        let c = b
9789            .as_any()
9790            .downcast_ref::<TimestampNanosecondArray>()
9791            .unwrap();
9792        assert_eq!(1609459200000000000, c.value(0));
9793        assert_eq!(1640995200000000000, c.value(1));
9794        assert!(c.is_null(2));
9795    }
9796
9797    #[test]
9798    fn test_cast_date32_to_timestamp_us_overflow() {
9799        const MAX_DAYS_MICROS: i32 = (i64::MAX / MICROSECONDS_IN_DAY) as i32;
9800        let a = Date32Array::from(vec![Some(MAX_DAYS_MICROS), Some(MAX_DAYS_MICROS + 1), None]);
9801        let array = Arc::new(a) as ArrayRef;
9802        let err = cast_with_options(
9803            &array,
9804            &DataType::Timestamp(TimeUnit::Microsecond, None),
9805            &CastOptions {
9806                safe: false,
9807                format_options: FormatOptions::default(),
9808            },
9809        );
9810        assert!(err.is_err());
9811
9812        let b = cast(&array, &DataType::Timestamp(TimeUnit::Microsecond, None)).unwrap();
9813        let c = b.as_primitive::<TimestampMicrosecondType>();
9814        assert_eq!(MAX_DAYS_MICROS as i64 * MICROSECONDS_IN_DAY, c.value(0));
9815        assert!(c.is_null(1));
9816        assert!(c.is_null(2));
9817    }
9818
9819    #[test]
9820    fn test_cast_date32_to_timestamp_ns_overflow() {
9821        // 2262-04-11, 2062-04-12
9822        let upper_limit = 106_751;
9823        let a = Date32Array::from(vec![Some(upper_limit), Some(upper_limit + 1), None]);
9824        let array = Arc::new(a) as ArrayRef;
9825        let err = cast_with_options(
9826            &array,
9827            &DataType::Timestamp(TimeUnit::Nanosecond, None),
9828            &CastOptions {
9829                safe: false,
9830                format_options: FormatOptions::default(),
9831            },
9832        );
9833        assert!(err.is_err());
9834
9835        let b = cast(&array, &DataType::Timestamp(TimeUnit::Nanosecond, None)).unwrap();
9836        let c = b.as_primitive::<TimestampNanosecondType>();
9837        assert_eq!(upper_limit as i64 * NANOSECONDS_IN_DAY, c.value(0));
9838        assert!(c.is_null(1));
9839        assert!(c.is_null(2));
9840    }
9841
9842    #[test]
9843    fn test_timezone_cast() {
9844        let a = StringArray::from(vec![
9845            "2000-01-01T12:00:00", // date + time valid
9846            "2020-12-15T12:34:56", // date + time valid
9847        ]);
9848        let array = Arc::new(a) as ArrayRef;
9849        let b = cast(&array, &DataType::Timestamp(TimeUnit::Nanosecond, None)).unwrap();
9850        let v = b.as_primitive::<TimestampNanosecondType>();
9851
9852        assert_eq!(v.value(0), 946728000000000000);
9853        assert_eq!(v.value(1), 1608035696000000000);
9854
9855        let b = cast(
9856            &b,
9857            &DataType::Timestamp(TimeUnit::Nanosecond, Some("+00:00".into())),
9858        )
9859        .unwrap();
9860        let v = b.as_primitive::<TimestampNanosecondType>();
9861
9862        assert_eq!(v.value(0), 946728000000000000);
9863        assert_eq!(v.value(1), 1608035696000000000);
9864
9865        let b = cast(
9866            &b,
9867            &DataType::Timestamp(TimeUnit::Millisecond, Some("+02:00".into())),
9868        )
9869        .unwrap();
9870        let v = b.as_primitive::<TimestampMillisecondType>();
9871
9872        assert_eq!(v.value(0), 946728000000);
9873        assert_eq!(v.value(1), 1608035696000);
9874    }
9875
9876    #[test]
9877    fn test_cast_utf8_to_timestamp() {
9878        fn test_tz(tz: Arc<str>) {
9879            let valid = StringArray::from(vec![
9880                "2023-01-01 04:05:06.789000-08:00",
9881                "2023-01-01 04:05:06.789000-07:00",
9882                "2023-01-01 04:05:06.789 -0800",
9883                "2023-01-01 04:05:06.789 -08:00",
9884                "2023-01-01 040506 +0730",
9885                "2023-01-01 040506 +07:30",
9886                "2023-01-01 04:05:06.789",
9887                "2023-01-01 04:05:06",
9888                "2023-01-01",
9889            ]);
9890
9891            let array = Arc::new(valid) as ArrayRef;
9892            let b = cast_with_options(
9893                &array,
9894                &DataType::Timestamp(TimeUnit::Nanosecond, Some(tz.clone())),
9895                &CastOptions {
9896                    safe: false,
9897                    format_options: FormatOptions::default(),
9898                },
9899            )
9900            .unwrap();
9901
9902            let tz = tz.as_ref().parse().unwrap();
9903
9904            let as_tz =
9905                |v: i64| as_datetime_with_timezone::<TimestampNanosecondType>(v, tz).unwrap();
9906
9907            let as_utc = |v: &i64| as_tz(*v).naive_utc().to_string();
9908            let as_local = |v: &i64| as_tz(*v).naive_local().to_string();
9909
9910            let values = b.as_primitive::<TimestampNanosecondType>().values();
9911            let utc_results: Vec<_> = values.iter().map(as_utc).collect();
9912            let local_results: Vec<_> = values.iter().map(as_local).collect();
9913
9914            // Absolute timestamps should be parsed preserving the same UTC instant
9915            assert_eq!(
9916                &utc_results[..6],
9917                &[
9918                    "2023-01-01 12:05:06.789".to_string(),
9919                    "2023-01-01 11:05:06.789".to_string(),
9920                    "2023-01-01 12:05:06.789".to_string(),
9921                    "2023-01-01 12:05:06.789".to_string(),
9922                    "2022-12-31 20:35:06".to_string(),
9923                    "2022-12-31 20:35:06".to_string(),
9924                ]
9925            );
9926            // Non-absolute timestamps should be parsed preserving the same local instant
9927            assert_eq!(
9928                &local_results[6..],
9929                &[
9930                    "2023-01-01 04:05:06.789".to_string(),
9931                    "2023-01-01 04:05:06".to_string(),
9932                    "2023-01-01 00:00:00".to_string()
9933                ]
9934            )
9935        }
9936
9937        test_tz("+00:00".into());
9938        test_tz("+02:00".into());
9939    }
9940
9941    #[test]
9942    fn test_cast_invalid_utf8() {
9943        let v1: &[u8] = b"\xFF invalid";
9944        let v2: &[u8] = b"\x00 Foo";
9945        let s = BinaryArray::from(vec![v1, v2]);
9946        let options = CastOptions {
9947            safe: true,
9948            format_options: FormatOptions::default(),
9949        };
9950        let array = cast_with_options(&s, &DataType::Utf8, &options).unwrap();
9951        let a = array.as_string::<i32>();
9952        a.to_data().validate_full().unwrap();
9953
9954        assert_eq!(a.null_count(), 1);
9955        assert_eq!(a.len(), 2);
9956        assert!(a.is_null(0));
9957        assert_eq!(a.value(0), "");
9958        assert_eq!(a.value(1), "\x00 Foo");
9959    }
9960
9961    #[test]
9962    fn test_cast_sliced_binary_with_hidden_invalid_utf8() {
9963        // The invalid first value is outside the slice, so it must not fail the cast
9964        let values: Vec<&[u8]> = vec![b"\xFF", b"a", b"b", b"c", b"d", b"e", b"f"];
9965        let arrays: [ArrayRef; 2] = [
9966            Arc::new(BinaryArray::from(values.clone()).slice(1, 6)),
9967            Arc::new(LargeBinaryArray::from(values).slice(1, 6)),
9968        ];
9969        let options = CastOptions {
9970            safe: false,
9971            format_options: FormatOptions::default(),
9972        };
9973        let expected = StringArray::from(vec!["a", "b", "c", "d", "e", "f"]);
9974        for array in &arrays {
9975            for to_type in [DataType::Utf8, DataType::LargeUtf8, DataType::Utf8View] {
9976                let result = cast_with_options(array, &to_type, &options).unwrap();
9977                assert_eq!(result.as_ref(), cast(&expected, &to_type).unwrap().as_ref());
9978            }
9979
9980            // A dictionary with fewer keys than half its values takes a separate
9981            // path to Utf8View
9982            let keys = Int32Array::from(vec![5, 0]);
9983            let dict = DictionaryArray::try_new(keys, Arc::clone(array)).unwrap();
9984            let result = cast_with_options(&dict, &DataType::Utf8View, &options).unwrap();
9985            assert_eq!(result.as_ref(), &StringViewArray::from(vec!["f", "a"]));
9986        }
9987    }
9988
9989    #[test]
9990    fn test_cast_utf8_to_timestamptz() {
9991        let valid = StringArray::from(vec!["2023-01-01"]);
9992
9993        let array = Arc::new(valid) as ArrayRef;
9994        let b = cast(
9995            &array,
9996            &DataType::Timestamp(TimeUnit::Nanosecond, Some("+00:00".into())),
9997        )
9998        .unwrap();
9999
10000        let expect = DataType::Timestamp(TimeUnit::Nanosecond, Some("+00:00".into()));
10001
10002        assert_eq!(b.data_type(), &expect);
10003        let c = b
10004            .as_any()
10005            .downcast_ref::<TimestampNanosecondArray>()
10006            .unwrap();
10007        assert_eq!(1672531200000000000, c.value(0));
10008    }
10009
10010    #[test]
10011    fn test_cast_out_of_precision_decimal_to_string() {
10012        // Decimal values are not validated against their type's declared
10013        // precision by default. Check that out-of-precision values are rendered
10014        // in full when cast to strings, rather than truncated to the declared
10015        // precision (https://github.com/apache/arrow-rs/issues/10866)
10016        let array = create_decimal128_array(vec![Some(123456789), Some(-123456789)], 7, 3).unwrap();
10017        let b = cast(&array, &DataType::Utf8).unwrap();
10018        let c = b.as_string::<i32>();
10019        assert_eq!("123456.789", c.value(0));
10020        assert_eq!("-123456.789", c.value(1));
10021    }
10022
10023    #[test]
10024    fn test_cast_decimal_to_string() {
10025        assert!(can_cast_types(
10026            &DataType::Decimal32(9, 4),
10027            &DataType::Utf8View
10028        ));
10029        assert!(can_cast_types(
10030            &DataType::Decimal64(16, 4),
10031            &DataType::Utf8View
10032        ));
10033        assert!(can_cast_types(
10034            &DataType::Decimal128(10, 4),
10035            &DataType::Utf8View
10036        ));
10037        assert!(can_cast_types(
10038            &DataType::Decimal256(38, 10),
10039            &DataType::Utf8View
10040        ));
10041
10042        macro_rules! assert_decimal_values {
10043            ($array:expr) => {
10044                let c = $array;
10045                assert_eq!("1123.454", c.value(0));
10046                assert_eq!("2123.456", c.value(1));
10047                assert_eq!("-3123.453", c.value(2));
10048                assert_eq!("-3123.456", c.value(3));
10049                assert_eq!("0.000", c.value(4));
10050                assert_eq!("0.123", c.value(5));
10051                assert!(c.is_null(6));
10052            };
10053        }
10054
10055        fn test_decimal_to_string<IN: ArrowPrimitiveType, OffsetSize: OffsetSizeTrait>(
10056            output_type: DataType,
10057            array: PrimitiveArray<IN>,
10058        ) {
10059            let b = cast(&array, &output_type).unwrap();
10060
10061            assert_eq!(b.data_type(), &output_type);
10062            match b.data_type() {
10063                DataType::Utf8View => {
10064                    let c = b.as_string_view();
10065                    assert_decimal_values!(c);
10066                }
10067                DataType::Utf8 | DataType::LargeUtf8 => {
10068                    let c = b.as_string::<OffsetSize>();
10069                    assert_decimal_values!(c);
10070                }
10071                _ => (),
10072            }
10073        }
10074
10075        let array32: Vec<Option<i32>> = vec![
10076            Some(1123454),
10077            Some(2123456),
10078            Some(-3123453),
10079            Some(-3123456),
10080            Some(0),
10081            Some(123),
10082            None,
10083        ];
10084        let array64: Vec<Option<i64>> = array32.iter().map(|num| num.map(|x| x as i64)).collect();
10085        let array128: Vec<Option<i128>> =
10086            array64.iter().map(|num| num.map(|x| x as i128)).collect();
10087        let array256: Vec<Option<i256>> = array128
10088            .iter()
10089            .map(|num| num.map(i256::from_i128))
10090            .collect();
10091
10092        test_decimal_to_string::<Decimal32Type, i32>(
10093            DataType::Utf8View,
10094            create_decimal32_array(array32.clone(), 7, 3).unwrap(),
10095        );
10096        test_decimal_to_string::<Decimal32Type, i32>(
10097            DataType::Utf8,
10098            create_decimal32_array(array32.clone(), 7, 3).unwrap(),
10099        );
10100        test_decimal_to_string::<Decimal32Type, i64>(
10101            DataType::LargeUtf8,
10102            create_decimal32_array(array32, 7, 3).unwrap(),
10103        );
10104
10105        test_decimal_to_string::<Decimal64Type, i32>(
10106            DataType::Utf8View,
10107            create_decimal64_array(array64.clone(), 7, 3).unwrap(),
10108        );
10109        test_decimal_to_string::<Decimal64Type, i32>(
10110            DataType::Utf8,
10111            create_decimal64_array(array64.clone(), 7, 3).unwrap(),
10112        );
10113        test_decimal_to_string::<Decimal64Type, i64>(
10114            DataType::LargeUtf8,
10115            create_decimal64_array(array64, 7, 3).unwrap(),
10116        );
10117
10118        test_decimal_to_string::<Decimal128Type, i32>(
10119            DataType::Utf8View,
10120            create_decimal128_array(array128.clone(), 7, 3).unwrap(),
10121        );
10122        test_decimal_to_string::<Decimal128Type, i32>(
10123            DataType::Utf8,
10124            create_decimal128_array(array128.clone(), 7, 3).unwrap(),
10125        );
10126        test_decimal_to_string::<Decimal128Type, i64>(
10127            DataType::LargeUtf8,
10128            create_decimal128_array(array128, 7, 3).unwrap(),
10129        );
10130
10131        test_decimal_to_string::<Decimal256Type, i32>(
10132            DataType::Utf8View,
10133            create_decimal256_array(array256.clone(), 7, 3).unwrap(),
10134        );
10135        test_decimal_to_string::<Decimal256Type, i32>(
10136            DataType::Utf8,
10137            create_decimal256_array(array256.clone(), 7, 3).unwrap(),
10138        );
10139        test_decimal_to_string::<Decimal256Type, i64>(
10140            DataType::LargeUtf8,
10141            create_decimal256_array(array256, 7, 3).unwrap(),
10142        );
10143    }
10144
10145    #[test]
10146    fn test_cast_numeric_to_decimal128_precision_overflow() {
10147        let array = Int64Array::from(vec![1234567]);
10148        let array = Arc::new(array) as ArrayRef;
10149        let casted_array = cast_with_options(
10150            &array,
10151            &DataType::Decimal128(7, 3),
10152            &CastOptions {
10153                safe: true,
10154                format_options: FormatOptions::default(),
10155            },
10156        );
10157        assert!(casted_array.is_ok());
10158        assert!(casted_array.unwrap().is_null(0));
10159
10160        let err = cast_with_options(
10161            &array,
10162            &DataType::Decimal128(7, 3),
10163            &CastOptions {
10164                safe: false,
10165                format_options: FormatOptions::default(),
10166            },
10167        );
10168        assert_eq!(
10169            "Invalid argument error: 1234567.000 is too large to store in a Decimal128 of precision 7. Max is 9999.999",
10170            err.unwrap_err().to_string()
10171        );
10172    }
10173
10174    #[test]
10175    fn test_cast_numeric_to_decimal256_precision_overflow() {
10176        let array = Int64Array::from(vec![1234567]);
10177        let array = Arc::new(array) as ArrayRef;
10178        let casted_array = cast_with_options(
10179            &array,
10180            &DataType::Decimal256(7, 3),
10181            &CastOptions {
10182                safe: true,
10183                format_options: FormatOptions::default(),
10184            },
10185        );
10186        assert!(casted_array.is_ok());
10187        assert!(casted_array.unwrap().is_null(0));
10188
10189        let err = cast_with_options(
10190            &array,
10191            &DataType::Decimal256(7, 3),
10192            &CastOptions {
10193                safe: false,
10194                format_options: FormatOptions::default(),
10195            },
10196        );
10197        assert_eq!(
10198            "Invalid argument error: 1234567.000 is too large to store in a Decimal256 of precision 7. Max is 9999.999",
10199            err.unwrap_err().to_string()
10200        );
10201    }
10202
10203    /// helper function to test casting from duration to interval
10204    fn cast_from_duration_to_interval<T: ArrowTemporalType<Native = i64>>(
10205        array: Vec<i64>,
10206        cast_options: &CastOptions,
10207    ) -> Result<PrimitiveArray<IntervalMonthDayNanoType>, ArrowError> {
10208        let array = PrimitiveArray::<T>::new(array.into(), None);
10209        let array = Arc::new(array) as ArrayRef;
10210        let interval = DataType::Interval(IntervalUnit::MonthDayNano);
10211        let out = cast_with_options(&array, &interval, cast_options)?;
10212        let out = out.as_primitive::<IntervalMonthDayNanoType>().clone();
10213        Ok(out)
10214    }
10215
10216    #[test]
10217    fn test_cast_from_duration_to_interval() {
10218        // from duration second to interval month day nano
10219        let array = vec![1234567];
10220        let casted_array =
10221            cast_from_duration_to_interval::<DurationSecondType>(array, &CastOptions::default())
10222                .unwrap();
10223        assert_eq!(
10224            casted_array.data_type(),
10225            &DataType::Interval(IntervalUnit::MonthDayNano)
10226        );
10227        assert_eq!(
10228            casted_array.value(0),
10229            IntervalMonthDayNano::new(0, 0, 1234567000000000)
10230        );
10231
10232        let array = vec![i64::MAX];
10233        let casted_array = cast_from_duration_to_interval::<DurationSecondType>(
10234            array.clone(),
10235            &CastOptions::default(),
10236        )
10237        .unwrap();
10238        assert!(!casted_array.is_valid(0));
10239
10240        let casted_array = cast_from_duration_to_interval::<DurationSecondType>(
10241            array,
10242            &CastOptions {
10243                safe: false,
10244                format_options: FormatOptions::default(),
10245            },
10246        );
10247        assert!(casted_array.is_err());
10248
10249        // from duration millisecond to interval month day nano
10250        let array = vec![1234567];
10251        let casted_array = cast_from_duration_to_interval::<DurationMillisecondType>(
10252            array,
10253            &CastOptions::default(),
10254        )
10255        .unwrap();
10256        assert_eq!(
10257            casted_array.data_type(),
10258            &DataType::Interval(IntervalUnit::MonthDayNano)
10259        );
10260        assert_eq!(
10261            casted_array.value(0),
10262            IntervalMonthDayNano::new(0, 0, 1234567000000)
10263        );
10264
10265        let array = vec![i64::MAX];
10266        let casted_array = cast_from_duration_to_interval::<DurationMillisecondType>(
10267            array.clone(),
10268            &CastOptions::default(),
10269        )
10270        .unwrap();
10271        assert!(!casted_array.is_valid(0));
10272
10273        let casted_array = cast_from_duration_to_interval::<DurationMillisecondType>(
10274            array,
10275            &CastOptions {
10276                safe: false,
10277                format_options: FormatOptions::default(),
10278            },
10279        );
10280        assert!(casted_array.is_err());
10281
10282        // from duration microsecond to interval month day nano
10283        let array = vec![1234567];
10284        let casted_array = cast_from_duration_to_interval::<DurationMicrosecondType>(
10285            array,
10286            &CastOptions::default(),
10287        )
10288        .unwrap();
10289        assert_eq!(
10290            casted_array.data_type(),
10291            &DataType::Interval(IntervalUnit::MonthDayNano)
10292        );
10293        assert_eq!(
10294            casted_array.value(0),
10295            IntervalMonthDayNano::new(0, 0, 1234567000)
10296        );
10297
10298        let array = vec![i64::MAX];
10299        let casted_array = cast_from_duration_to_interval::<DurationMicrosecondType>(
10300            array.clone(),
10301            &CastOptions::default(),
10302        )
10303        .unwrap();
10304        assert!(!casted_array.is_valid(0));
10305
10306        let casted_array = cast_from_duration_to_interval::<DurationMicrosecondType>(
10307            array,
10308            &CastOptions {
10309                safe: false,
10310                format_options: FormatOptions::default(),
10311            },
10312        );
10313        assert!(casted_array.is_err());
10314
10315        // from duration nanosecond to interval month day nano
10316        let array = vec![1234567];
10317        let casted_array = cast_from_duration_to_interval::<DurationNanosecondType>(
10318            array,
10319            &CastOptions::default(),
10320        )
10321        .unwrap();
10322        assert_eq!(
10323            casted_array.data_type(),
10324            &DataType::Interval(IntervalUnit::MonthDayNano)
10325        );
10326        assert_eq!(
10327            casted_array.value(0),
10328            IntervalMonthDayNano::new(0, 0, 1234567)
10329        );
10330
10331        let array = vec![i64::MAX];
10332        let casted_array = cast_from_duration_to_interval::<DurationNanosecondType>(
10333            array,
10334            &CastOptions {
10335                safe: false,
10336                format_options: FormatOptions::default(),
10337            },
10338        )
10339        .unwrap();
10340        assert_eq!(
10341            casted_array.value(0),
10342            IntervalMonthDayNano::new(0, 0, i64::MAX)
10343        );
10344    }
10345
10346    /// helper function to test casting from interval to duration
10347    fn cast_from_interval_to_duration<T: ArrowTemporalType>(
10348        array: &IntervalMonthDayNanoArray,
10349        cast_options: &CastOptions,
10350    ) -> Result<PrimitiveArray<T>, ArrowError> {
10351        let casted_array = cast_with_options(&array, &T::DATA_TYPE, cast_options)?;
10352        casted_array
10353            .as_any()
10354            .downcast_ref::<PrimitiveArray<T>>()
10355            .ok_or_else(|| {
10356                ArrowError::ComputeError(format!("Failed to downcast to {}", T::DATA_TYPE))
10357            })
10358            .cloned()
10359    }
10360
10361    #[test]
10362    fn test_cast_from_interval_to_duration() {
10363        let nullable = CastOptions::default();
10364        let fallible = CastOptions {
10365            safe: false,
10366            format_options: FormatOptions::default(),
10367        };
10368        let v = IntervalMonthDayNano::new(0, 0, 1234567);
10369
10370        // from interval month day nano to duration second
10371        let array = vec![v].into();
10372        let casted_array: DurationSecondArray =
10373            cast_from_interval_to_duration(&array, &nullable).unwrap();
10374        assert_eq!(casted_array.value(0), 0);
10375
10376        let array = vec![IntervalMonthDayNano::MAX].into();
10377        let casted_array: DurationSecondArray =
10378            cast_from_interval_to_duration(&array, &nullable).unwrap();
10379        assert!(!casted_array.is_valid(0));
10380
10381        let res = cast_from_interval_to_duration::<DurationSecondType>(&array, &fallible);
10382        assert!(res.is_err());
10383
10384        // from interval month day nano to duration millisecond
10385        let array = vec![v].into();
10386        let casted_array: DurationMillisecondArray =
10387            cast_from_interval_to_duration(&array, &nullable).unwrap();
10388        assert_eq!(casted_array.value(0), 1);
10389
10390        let array = vec![IntervalMonthDayNano::MAX].into();
10391        let casted_array: DurationMillisecondArray =
10392            cast_from_interval_to_duration(&array, &nullable).unwrap();
10393        assert!(!casted_array.is_valid(0));
10394
10395        let res = cast_from_interval_to_duration::<DurationMillisecondType>(&array, &fallible);
10396        assert!(res.is_err());
10397
10398        // from interval month day nano to duration microsecond
10399        let array = vec![v].into();
10400        let casted_array: DurationMicrosecondArray =
10401            cast_from_interval_to_duration(&array, &nullable).unwrap();
10402        assert_eq!(casted_array.value(0), 1234);
10403
10404        let array = vec![IntervalMonthDayNano::MAX].into();
10405        let casted_array =
10406            cast_from_interval_to_duration::<DurationMicrosecondType>(&array, &nullable).unwrap();
10407        assert!(!casted_array.is_valid(0));
10408
10409        let casted_array =
10410            cast_from_interval_to_duration::<DurationMicrosecondType>(&array, &fallible);
10411        assert!(casted_array.is_err());
10412
10413        // from interval month day nano to duration nanosecond
10414        let array = vec![v].into();
10415        let casted_array: DurationNanosecondArray =
10416            cast_from_interval_to_duration(&array, &nullable).unwrap();
10417        assert_eq!(casted_array.value(0), 1234567);
10418
10419        let array = vec![IntervalMonthDayNano::MAX].into();
10420        let casted_array: DurationNanosecondArray =
10421            cast_from_interval_to_duration(&array, &nullable).unwrap();
10422        assert!(!casted_array.is_valid(0));
10423
10424        let casted_array =
10425            cast_from_interval_to_duration::<DurationNanosecondType>(&array, &fallible);
10426        assert!(casted_array.is_err());
10427
10428        let array = vec![
10429            IntervalMonthDayNanoType::make_value(0, 1, 0),
10430            IntervalMonthDayNanoType::make_value(-1, 0, 0),
10431            IntervalMonthDayNanoType::make_value(1, 1, 0),
10432            IntervalMonthDayNanoType::make_value(1, 0, 1),
10433            IntervalMonthDayNanoType::make_value(0, 0, -1),
10434        ]
10435        .into();
10436        let casted_array =
10437            cast_from_interval_to_duration::<DurationNanosecondType>(&array, &nullable).unwrap();
10438        assert!(!casted_array.is_valid(0));
10439        assert!(!casted_array.is_valid(1));
10440        assert!(!casted_array.is_valid(2));
10441        assert!(!casted_array.is_valid(3));
10442        assert!(casted_array.is_valid(4));
10443        assert_eq!(casted_array.value(4), -1);
10444    }
10445
10446    /// helper function to test casting from interval year month to interval month day nano
10447    fn cast_from_interval_year_month_to_interval_month_day_nano(
10448        array: Vec<i32>,
10449        cast_options: &CastOptions,
10450    ) -> Result<PrimitiveArray<IntervalMonthDayNanoType>, ArrowError> {
10451        let array = PrimitiveArray::<IntervalYearMonthType>::from(array);
10452        let array = Arc::new(array) as ArrayRef;
10453        let casted_array = cast_with_options(
10454            &array,
10455            &DataType::Interval(IntervalUnit::MonthDayNano),
10456            cast_options,
10457        )?;
10458        casted_array
10459            .as_any()
10460            .downcast_ref::<IntervalMonthDayNanoArray>()
10461            .ok_or_else(|| {
10462                ArrowError::ComputeError(
10463                    "Failed to downcast to IntervalMonthDayNanoArray".to_string(),
10464                )
10465            })
10466            .cloned()
10467    }
10468
10469    #[test]
10470    fn test_cast_from_interval_year_month_to_interval_month_day_nano() {
10471        // from interval year month to interval month day nano
10472        let array = vec![1234567];
10473        let casted_array = cast_from_interval_year_month_to_interval_month_day_nano(
10474            array,
10475            &CastOptions::default(),
10476        )
10477        .unwrap();
10478        assert_eq!(
10479            casted_array.data_type(),
10480            &DataType::Interval(IntervalUnit::MonthDayNano)
10481        );
10482        assert_eq!(
10483            casted_array.value(0),
10484            IntervalMonthDayNano::new(1234567, 0, 0)
10485        );
10486    }
10487
10488    /// helper function to test casting from interval day time to interval month day nano
10489    fn cast_from_interval_day_time_to_interval_month_day_nano(
10490        array: Vec<IntervalDayTime>,
10491        cast_options: &CastOptions,
10492    ) -> Result<PrimitiveArray<IntervalMonthDayNanoType>, ArrowError> {
10493        let array = PrimitiveArray::<IntervalDayTimeType>::from(array);
10494        let array = Arc::new(array) as ArrayRef;
10495        let casted_array = cast_with_options(
10496            &array,
10497            &DataType::Interval(IntervalUnit::MonthDayNano),
10498            cast_options,
10499        )?;
10500        Ok(casted_array
10501            .as_primitive::<IntervalMonthDayNanoType>()
10502            .clone())
10503    }
10504
10505    #[test]
10506    fn test_cast_from_interval_day_time_to_interval_month_day_nano() {
10507        // from interval day time to interval month day nano
10508        let array = vec![IntervalDayTime::new(123, 0)];
10509        let casted_array =
10510            cast_from_interval_day_time_to_interval_month_day_nano(array, &CastOptions::default())
10511                .unwrap();
10512        assert_eq!(
10513            casted_array.data_type(),
10514            &DataType::Interval(IntervalUnit::MonthDayNano)
10515        );
10516        assert_eq!(casted_array.value(0), IntervalMonthDayNano::new(0, 123, 0));
10517    }
10518
10519    #[test]
10520    fn test_can_cast_interval_to_int64_matches_cast() {
10521        // Assert the two agree for every interval unit, rather than hard coding the answer.
10522        let arrays: Vec<ArrayRef> = vec![
10523            Arc::new(IntervalYearMonthArray::from(vec![12])),
10524            Arc::new(IntervalDayTimeArray::from(vec![IntervalDayTime::new(1, 2)])),
10525            Arc::new(IntervalMonthDayNanoArray::from(vec![
10526                IntervalMonthDayNano::new(1, 2, 3),
10527            ])),
10528        ];
10529        for array in arrays {
10530            let from = array.data_type();
10531            assert_eq!(
10532                can_cast_types(from, &DataType::Int64),
10533                cast(&array, &DataType::Int64).is_ok(),
10534                "can_cast_types disagrees with cast for {from} -> Int64"
10535            );
10536        }
10537    }
10538
10539    #[test]
10540    fn test_cast_union_to_int64_skips_uncastable_interval_child() {
10541        // `resolve_child_array` picks the first child `can_cast_types` accepts, so an
10542        // over-permissive answer made it pick the interval child instead of the `Utf8` one.
10543        let fields = UnionFields::try_new(
10544            [0, 1],
10545            [
10546                Field::new("iv", DataType::Interval(IntervalUnit::YearMonth), true),
10547                Field::new("s", DataType::Utf8, true),
10548            ],
10549        )
10550        .unwrap();
10551        let union = UnionArray::try_new(
10552            fields,
10553            vec![0, 1, 0].into(),
10554            None,
10555            vec![
10556                Arc::new(IntervalYearMonthArray::from(vec![Some(12), None, Some(24)])),
10557                Arc::new(StringArray::from(vec![None, Some("77"), None])),
10558            ],
10559        )
10560        .unwrap();
10561
10562        let casted = cast(&union, &DataType::Int64).unwrap();
10563        let casted = casted.as_primitive::<Int64Type>();
10564        assert!(casted.is_null(0));
10565        assert_eq!(casted.value(1), 77);
10566        assert!(casted.is_null(2));
10567    }
10568
10569    #[test]
10570    fn test_cast_below_unixtimestamp() {
10571        let valid = StringArray::from(vec![
10572            "1900-01-03 23:59:59",
10573            "1969-12-31 00:00:01",
10574            "1989-12-31 00:00:01",
10575        ]);
10576
10577        let array = Arc::new(valid) as ArrayRef;
10578        let casted_array = cast_with_options(
10579            &array,
10580            &DataType::Timestamp(TimeUnit::Nanosecond, Some("+00:00".into())),
10581            &CastOptions {
10582                safe: false,
10583                format_options: FormatOptions::default(),
10584            },
10585        )
10586        .unwrap();
10587
10588        let ts_array = casted_array
10589            .as_primitive::<TimestampNanosecondType>()
10590            .values()
10591            .iter()
10592            .map(|ts| ts / 1_000_000)
10593            .collect::<Vec<_>>();
10594
10595        let array = TimestampMillisecondArray::from(ts_array).with_timezone("+00:00".to_string());
10596        let casted_array = cast(&array, &DataType::Date32).unwrap();
10597        let date_array = casted_array.as_primitive::<Date32Type>();
10598        let casted_array = cast(&date_array, &DataType::Utf8).unwrap();
10599        let string_array = casted_array.as_string::<i32>();
10600        assert_eq!("1900-01-03", string_array.value(0));
10601        assert_eq!("1969-12-31", string_array.value(1));
10602        assert_eq!("1989-12-31", string_array.value(2));
10603    }
10604
10605    const CAST_OPTIONS: CastOptions<'static> = CastOptions {
10606        safe: true,
10607        format_options: FormatOptions::new(),
10608    };
10609
10610    #[test]
10611    #[expect(clippy::assertions_on_constants)]
10612    fn test_const_options() {
10613        assert!(CAST_OPTIONS.safe)
10614    }
10615
10616    #[test]
10617    fn test_cast_string_to_timestamp_invalid_tz() {
10618        // content after Z should be ignored
10619        let bad_timestamp = "2023-12-05T21:58:10.45ZZTOP";
10620        let array = StringArray::from(vec![Some(bad_timestamp)]);
10621
10622        let data_types = [
10623            DataType::Timestamp(TimeUnit::Second, None),
10624            DataType::Timestamp(TimeUnit::Millisecond, None),
10625            DataType::Timestamp(TimeUnit::Microsecond, None),
10626            DataType::Timestamp(TimeUnit::Nanosecond, None),
10627        ];
10628
10629        let cast_options = CastOptions {
10630            safe: false,
10631            ..Default::default()
10632        };
10633
10634        for dt in data_types {
10635            // The trailing detail of the message differs depending on whether
10636            // `chrono-tz` is enabled, so only the common prefix is asserted.
10637            let err = cast_with_options(&array, &dt, &cast_options)
10638                .unwrap_err()
10639                .to_string();
10640            assert!(
10641                err.starts_with("Parser error: Invalid timezone \"ZZTOP\":"),
10642                "{err}"
10643            );
10644        }
10645    }
10646    #[test]
10647    fn test_cast_struct_to_struct() {
10648        let struct_type = DataType::Struct(
10649            vec![
10650                Field::new("a", DataType::Boolean, false),
10651                Field::new("b", DataType::Int32, false),
10652            ]
10653            .into(),
10654        );
10655        let to_type = DataType::Struct(
10656            vec![
10657                Field::new("a", DataType::Utf8, false),
10658                Field::new("b", DataType::Utf8, false),
10659            ]
10660            .into(),
10661        );
10662        let boolean = Arc::new(BooleanArray::from(vec![false, false, true, true]));
10663        let int = Arc::new(Int32Array::from(vec![42, 28, 19, 31]));
10664        let struct_array = StructArray::from(vec![
10665            (
10666                Arc::new(Field::new("b", DataType::Boolean, false)),
10667                boolean.clone() as ArrayRef,
10668            ),
10669            (
10670                Arc::new(Field::new("c", DataType::Int32, false)),
10671                int.clone() as ArrayRef,
10672            ),
10673        ]);
10674        let casted_array = cast(&struct_array, &to_type).unwrap();
10675        let casted_array = casted_array.as_struct();
10676        assert_eq!(casted_array.data_type(), &to_type);
10677        let casted_boolean_array = casted_array
10678            .column(0)
10679            .as_string::<i32>()
10680            .into_iter()
10681            .flatten()
10682            .collect::<Vec<_>>();
10683        let casted_int_array = casted_array
10684            .column(1)
10685            .as_string::<i32>()
10686            .into_iter()
10687            .flatten()
10688            .collect::<Vec<_>>();
10689        assert_eq!(casted_boolean_array, vec!["false", "false", "true", "true"]);
10690        assert_eq!(casted_int_array, vec!["42", "28", "19", "31"]);
10691
10692        // test for can't cast
10693        let to_type = DataType::Struct(
10694            vec![
10695                Field::new("a", DataType::Date32, false),
10696                Field::new("b", DataType::Utf8, false),
10697            ]
10698            .into(),
10699        );
10700        assert!(!can_cast_types(&struct_type, &to_type));
10701        let result = cast(&struct_array, &to_type);
10702        assert_eq!(
10703            "Cast error: Casting from Boolean to Date32 not supported",
10704            result.unwrap_err().to_string()
10705        );
10706    }
10707
10708    #[test]
10709    fn test_cast_struct_to_struct_nullability() {
10710        let boolean = Arc::new(BooleanArray::from(vec![false, false, true, true]));
10711        let int = Arc::new(Int32Array::from(vec![Some(42), None, Some(19), None]));
10712        let struct_array = StructArray::from(vec![
10713            (
10714                Arc::new(Field::new("b", DataType::Boolean, false)),
10715                boolean.clone() as ArrayRef,
10716            ),
10717            (
10718                Arc::new(Field::new("c", DataType::Int32, true)),
10719                int.clone() as ArrayRef,
10720            ),
10721        ]);
10722
10723        // okay: nullable to nullable
10724        let to_type = DataType::Struct(
10725            vec![
10726                Field::new("a", DataType::Utf8, false),
10727                Field::new("b", DataType::Utf8, true),
10728            ]
10729            .into(),
10730        );
10731        cast(&struct_array, &to_type).expect("Cast nullable to nullable struct field should work");
10732
10733        // error: nullable to non-nullable
10734        let to_type = DataType::Struct(
10735            vec![
10736                Field::new("a", DataType::Utf8, false),
10737                Field::new("b", DataType::Utf8, false),
10738            ]
10739            .into(),
10740        );
10741        cast(&struct_array, &to_type)
10742            .expect_err("Cast nullable to non-nullable struct field should fail");
10743
10744        let boolean = Arc::new(BooleanArray::from(vec![false, false, true, true]));
10745        let int = Arc::new(Int32Array::from(vec![i32::MAX, 25, 1, 100]));
10746        let struct_array = StructArray::from(vec![
10747            (
10748                Arc::new(Field::new("b", DataType::Boolean, false)),
10749                boolean.clone() as ArrayRef,
10750            ),
10751            (
10752                Arc::new(Field::new("c", DataType::Int32, false)),
10753                int.clone() as ArrayRef,
10754            ),
10755        ]);
10756
10757        // okay: non-nullable to non-nullable
10758        let to_type = DataType::Struct(
10759            vec![
10760                Field::new("a", DataType::Utf8, false),
10761                Field::new("b", DataType::Utf8, false),
10762            ]
10763            .into(),
10764        );
10765        cast(&struct_array, &to_type)
10766            .expect("Cast non-nullable to non-nullable struct field should work");
10767
10768        // err: non-nullable to non-nullable but overflowing return null during casting
10769        let to_type = DataType::Struct(
10770            vec![
10771                Field::new("a", DataType::Utf8, false),
10772                Field::new("b", DataType::Int8, false),
10773            ]
10774            .into(),
10775        );
10776        cast(&struct_array, &to_type).expect_err(
10777            "Cast non-nullable to non-nullable struct field returning null should fail",
10778        );
10779    }
10780
10781    #[test]
10782    fn test_cast_struct_to_non_struct() {
10783        let boolean = Arc::new(BooleanArray::from(vec![true, false]));
10784        let struct_array = StructArray::from(vec![(
10785            Arc::new(Field::new("a", DataType::Boolean, false)),
10786            boolean.clone() as ArrayRef,
10787        )]);
10788        let to_type = DataType::Utf8;
10789        let result = cast(&struct_array, &to_type);
10790        assert_eq!(
10791            r#"Cast error: Casting from Struct("a": non-null Boolean) to Utf8 not supported"#,
10792            result.unwrap_err().to_string()
10793        );
10794    }
10795
10796    #[test]
10797    fn test_cast_non_struct_to_struct() {
10798        let array = StringArray::from(vec!["a", "b"]);
10799        let to_type = DataType::Struct(vec![Field::new("a", DataType::Boolean, false)].into());
10800        let result = cast(&array, &to_type);
10801        assert_eq!(
10802            r#"Cast error: Casting from Utf8 to Struct("a": non-null Boolean) not supported"#,
10803            result.unwrap_err().to_string()
10804        );
10805    }
10806
10807    #[test]
10808    fn test_cast_struct_with_different_field_order() {
10809        // Test slow path: fields are in different order
10810        let boolean = Arc::new(BooleanArray::from(vec![false, false, true, true]));
10811        let int = Arc::new(Int32Array::from(vec![42, 28, 19, 31]));
10812        let string = Arc::new(StringArray::from(vec!["foo", "bar", "baz", "qux"]));
10813
10814        let struct_array = StructArray::from(vec![
10815            (
10816                Arc::new(Field::new("a", DataType::Boolean, false)),
10817                boolean.clone() as ArrayRef,
10818            ),
10819            (
10820                Arc::new(Field::new("b", DataType::Int32, false)),
10821                int.clone() as ArrayRef,
10822            ),
10823            (
10824                Arc::new(Field::new("c", DataType::Utf8, false)),
10825                string.clone() as ArrayRef,
10826            ),
10827        ]);
10828
10829        // Target has fields in different order: c, a, b instead of a, b, c
10830        let to_type = DataType::Struct(
10831            vec![
10832                Field::new("c", DataType::Utf8, false),
10833                Field::new("a", DataType::Utf8, false), // Boolean to Utf8
10834                Field::new("b", DataType::Utf8, false), // Int32 to Utf8
10835            ]
10836            .into(),
10837        );
10838
10839        let result = cast(&struct_array, &to_type).unwrap();
10840        let result_struct = result.as_struct();
10841
10842        assert_eq!(result_struct.data_type(), &to_type);
10843        assert_eq!(result_struct.num_columns(), 3);
10844
10845        // Verify field "c" (originally position 2, now position 0) remains Utf8
10846        let c_column = result_struct.column(0).as_string::<i32>();
10847        assert_eq!(
10848            c_column.into_iter().flatten().collect::<Vec<_>>(),
10849            vec!["foo", "bar", "baz", "qux"]
10850        );
10851
10852        // Verify field "a" (originally position 0, now position 1) was cast from Boolean to Utf8
10853        let a_column = result_struct.column(1).as_string::<i32>();
10854        assert_eq!(
10855            a_column.into_iter().flatten().collect::<Vec<_>>(),
10856            vec!["false", "false", "true", "true"]
10857        );
10858
10859        // Verify field "b" (originally position 1, now position 2) was cast from Int32 to Utf8
10860        let b_column = result_struct.column(2).as_string::<i32>();
10861        assert_eq!(
10862            b_column.into_iter().flatten().collect::<Vec<_>>(),
10863            vec!["42", "28", "19", "31"]
10864        );
10865    }
10866
10867    #[test]
10868    fn test_cast_struct_with_missing_field() {
10869        // Test that casting fails when target has a field not present in source
10870        let boolean = Arc::new(BooleanArray::from(vec![false, true]));
10871        let struct_array = StructArray::from(vec![(
10872            Arc::new(Field::new("a", DataType::Boolean, false)),
10873            boolean.clone() as ArrayRef,
10874        )]);
10875
10876        let to_type = DataType::Struct(
10877            vec![
10878                Field::new("a", DataType::Utf8, false),
10879                Field::new("b", DataType::Int32, false), // Field "b" doesn't exist in source
10880            ]
10881            .into(),
10882        );
10883
10884        let result = cast(&struct_array, &to_type);
10885        assert!(result.is_err());
10886        assert_eq!(
10887            result.unwrap_err().to_string(),
10888            "Invalid argument error: Incorrect number of arrays for StructArray fields, expected 2 got 1"
10889        );
10890    }
10891
10892    #[test]
10893    fn test_cast_struct_with_subset_of_fields() {
10894        // Test casting to a struct with fewer fields (selecting a subset)
10895        let boolean = Arc::new(BooleanArray::from(vec![false, false, true, true]));
10896        let int = Arc::new(Int32Array::from(vec![42, 28, 19, 31]));
10897        let string = Arc::new(StringArray::from(vec!["foo", "bar", "baz", "qux"]));
10898
10899        let struct_array = StructArray::from(vec![
10900            (
10901                Arc::new(Field::new("a", DataType::Boolean, false)),
10902                boolean.clone() as ArrayRef,
10903            ),
10904            (
10905                Arc::new(Field::new("b", DataType::Int32, false)),
10906                int.clone() as ArrayRef,
10907            ),
10908            (
10909                Arc::new(Field::new("c", DataType::Utf8, false)),
10910                string.clone() as ArrayRef,
10911            ),
10912        ]);
10913
10914        // Target has only fields "c" and "a", omitting "b"
10915        let to_type = DataType::Struct(
10916            vec![
10917                Field::new("c", DataType::Utf8, false),
10918                Field::new("a", DataType::Utf8, false),
10919            ]
10920            .into(),
10921        );
10922
10923        let result = cast(&struct_array, &to_type).unwrap();
10924        let result_struct = result.as_struct();
10925
10926        assert_eq!(result_struct.data_type(), &to_type);
10927        assert_eq!(result_struct.num_columns(), 2);
10928
10929        // Verify field "c" remains Utf8
10930        let c_column = result_struct.column(0).as_string::<i32>();
10931        assert_eq!(
10932            c_column.into_iter().flatten().collect::<Vec<_>>(),
10933            vec!["foo", "bar", "baz", "qux"]
10934        );
10935
10936        // Verify field "a" was cast from Boolean to Utf8
10937        let a_column = result_struct.column(1).as_string::<i32>();
10938        assert_eq!(
10939            a_column.into_iter().flatten().collect::<Vec<_>>(),
10940            vec!["false", "false", "true", "true"]
10941        );
10942    }
10943
10944    #[test]
10945    fn test_can_cast_struct_rename_field() {
10946        // Test that can_cast_types returns false when target has a field not in source
10947        let from_type = DataType::Struct(
10948            vec![
10949                Field::new("a", DataType::Int32, false),
10950                Field::new("b", DataType::Utf8, false),
10951            ]
10952            .into(),
10953        );
10954
10955        let to_type = DataType::Struct(
10956            vec![
10957                Field::new("a", DataType::Int64, false),
10958                Field::new("c", DataType::Boolean, false), // Field "c" not in source
10959            ]
10960            .into(),
10961        );
10962
10963        assert!(can_cast_types(&from_type, &to_type));
10964    }
10965
10966    fn run_decimal_cast_test_case_between_multiple_types(t: DecimalCastTestConfig) {
10967        run_decimal_cast_test_case::<Decimal128Type, Decimal128Type>(t.clone());
10968        run_decimal_cast_test_case::<Decimal128Type, Decimal256Type>(t.clone());
10969        run_decimal_cast_test_case::<Decimal256Type, Decimal128Type>(t.clone());
10970        run_decimal_cast_test_case::<Decimal256Type, Decimal256Type>(t.clone());
10971    }
10972
10973    #[test]
10974    fn test_decimal_to_decimal_coverage() {
10975        let test_cases = [
10976            // increase precision, increase scale, infallible
10977            DecimalCastTestConfig {
10978                input_prec: 5,
10979                input_scale: 1,
10980                input_repr: 99999, // 9999.9
10981                output_prec: 10,
10982                output_scale: 6,
10983                expected_output_repr: Ok(9999900000), // 9999.900000
10984            },
10985            // increase precision, increase scale, fallible, safe
10986            DecimalCastTestConfig {
10987                input_prec: 5,
10988                input_scale: 1,
10989                input_repr: 99, // 9999.9
10990                output_prec: 7,
10991                output_scale: 6,
10992                expected_output_repr: Ok(9900000), // 9.900000
10993            },
10994            // increase precision, increase scale, fallible, unsafe
10995            DecimalCastTestConfig {
10996                input_prec: 5,
10997                input_scale: 1,
10998                input_repr: 99999, // 9999.9
10999                output_prec: 7,
11000                output_scale: 6,
11001                expected_output_repr: Err("Invalid argument error: 9999.900000 is too large to store in a {} of precision 7. Max is 9.999999".to_string()) // max is 9.999999
11002            },
11003            // increase precision, decrease scale, always infallible
11004            DecimalCastTestConfig {
11005                input_prec: 5,
11006                input_scale: 3,
11007                input_repr: 99999, // 99.999
11008                output_prec: 10,
11009                output_scale: 2,
11010                expected_output_repr: Ok(10000), // 100.00
11011            },
11012            // increase precision, decrease scale, no rounding
11013            DecimalCastTestConfig {
11014                input_prec: 5,
11015                input_scale: 3,
11016                input_repr: 99994, // 99.994
11017                output_prec: 10,
11018                output_scale: 2,
11019                expected_output_repr: Ok(9999), // 99.99
11020            },
11021            // increase precision, don't change scale, always infallible
11022            DecimalCastTestConfig {
11023                input_prec: 5,
11024                input_scale: 3,
11025                input_repr: 99999, // 99.999
11026                output_prec: 10,
11027                output_scale: 3,
11028                expected_output_repr: Ok(99999), // 99.999
11029            },
11030            // decrease precision, increase scale, safe
11031            DecimalCastTestConfig {
11032                input_prec: 10,
11033                input_scale: 5,
11034                input_repr: 999999, // 9.99999
11035                output_prec: 8,
11036                output_scale: 7,
11037                expected_output_repr: Ok(99999900), // 9.9999900
11038            },
11039            // decrease precision, increase scale, unsafe
11040            DecimalCastTestConfig {
11041                input_prec: 10,
11042                input_scale: 5,
11043                input_repr: 9999999, // 99.99999
11044                output_prec: 8,
11045                output_scale: 7,
11046                expected_output_repr: Err("Invalid argument error: 99.9999900 is too large to store in a {} of precision 8. Max is 9.9999999".to_string()) // max is 9.9999999
11047            },
11048            // decrease precision, decrease scale, safe, infallible
11049            DecimalCastTestConfig {
11050                input_prec: 7,
11051                input_scale: 4,
11052                input_repr: 9999999, // 999.9999
11053                output_prec: 6,
11054                output_scale: 2,
11055                expected_output_repr: Ok(100000),
11056            },
11057            // decrease precision, decrease scale, safe, fallible
11058            DecimalCastTestConfig {
11059                input_prec: 10,
11060                input_scale: 5,
11061                input_repr: 12345678, // 123.45678
11062                output_prec: 8,
11063                output_scale: 3,
11064                expected_output_repr: Ok(123457), // 123.457
11065            },
11066            // decrease precision, decrease scale, unsafe
11067            DecimalCastTestConfig {
11068                input_prec: 10,
11069                input_scale: 5,
11070                input_repr: 9999999, // 99.99999
11071                output_prec: 4,
11072                output_scale: 3,
11073                expected_output_repr: Err("Invalid argument error: 100.000 is too large to store in a {} of precision 4. Max is 9.999".to_string()) // max is 9.999
11074            },
11075            // decrease precision, same scale, safe
11076            DecimalCastTestConfig {
11077                input_prec: 10,
11078                input_scale: 5,
11079                input_repr: 999999, // 9.99999
11080                output_prec: 6,
11081                output_scale: 5,
11082                expected_output_repr: Ok(999999), // 9.99999
11083            },
11084            // decrease precision, same scale, unsafe
11085            DecimalCastTestConfig {
11086                input_prec: 10,
11087                input_scale: 5,
11088                input_repr: 9999999, // 99.99999
11089                output_prec: 6,
11090                output_scale: 5,
11091                expected_output_repr: Err("Invalid argument error: 99.99999 is too large to store in a {} of precision 6. Max is 9.99999".to_string()) // max is 9.99999
11092            },
11093            // same precision, increase scale, safe
11094            DecimalCastTestConfig {
11095                input_prec: 7,
11096                input_scale: 4,
11097                input_repr: 12345, // 1.2345
11098                output_prec: 7,
11099                output_scale: 6,
11100                expected_output_repr: Ok(1234500), // 1.234500
11101            },
11102            // same precision, increase scale, unsafe
11103            DecimalCastTestConfig {
11104                input_prec: 7,
11105                input_scale: 4,
11106                input_repr: 123456, // 12.3456
11107                output_prec: 7,
11108                output_scale: 6,
11109                expected_output_repr: Err("Invalid argument error: 12.345600 is too large to store in a {} of precision 7. Max is 9.999999".to_string()) // max is 9.99999
11110            },
11111            // same precision, decrease scale, infallible
11112            DecimalCastTestConfig {
11113                input_prec: 7,
11114                input_scale: 5,
11115                input_repr: 1234567, // 12.34567
11116                output_prec: 7,
11117                output_scale: 4,
11118                expected_output_repr: Ok(123457), // 12.3457
11119            },
11120            // same precision, same scale, infallible
11121            DecimalCastTestConfig {
11122                input_prec: 7,
11123                input_scale: 5,
11124                input_repr: 9999999, // 99.99999
11125                output_prec: 7,
11126                output_scale: 5,
11127                expected_output_repr: Ok(9999999), // 99.99999
11128            },
11129            // precision increase, input scale & output scale = 0, infallible
11130            DecimalCastTestConfig {
11131                input_prec: 7,
11132                input_scale: 0,
11133                input_repr: 1234567, // 1234567
11134                output_prec: 8,
11135                output_scale: 0,
11136                expected_output_repr: Ok(1234567), // 1234567
11137            },
11138            // precision decrease, input scale & output scale = 0, failure
11139            DecimalCastTestConfig {
11140                input_prec: 7,
11141                input_scale: 0,
11142                input_repr: 1234567, // 1234567
11143                output_prec: 6,
11144                output_scale: 0,
11145                expected_output_repr: Err("Invalid argument error: 1234567 is too large to store in a {} of precision 6. Max is 999999".to_string())
11146            },
11147            // precision decrease, input scale & output scale = 0, success
11148            DecimalCastTestConfig {
11149                input_prec: 7,
11150                input_scale: 0,
11151                input_repr: 123456, // 123456
11152                output_prec: 6,
11153                output_scale: 0,
11154                expected_output_repr: Ok(123456), // 123456
11155            },
11156        ];
11157
11158        for t in test_cases {
11159            run_decimal_cast_test_case_between_multiple_types(t);
11160        }
11161    }
11162
11163    #[test]
11164    fn test_decimal_to_decimal_increase_scale_and_precision_unchecked() {
11165        let test_cases = [
11166            DecimalCastTestConfig {
11167                input_prec: 5,
11168                input_scale: 0,
11169                input_repr: 99999,
11170                output_prec: 10,
11171                output_scale: 5,
11172                expected_output_repr: Ok(9999900000),
11173            },
11174            DecimalCastTestConfig {
11175                input_prec: 5,
11176                input_scale: 0,
11177                input_repr: -99999,
11178                output_prec: 10,
11179                output_scale: 5,
11180                expected_output_repr: Ok(-9999900000),
11181            },
11182            DecimalCastTestConfig {
11183                input_prec: 5,
11184                input_scale: 2,
11185                input_repr: 99999,
11186                output_prec: 10,
11187                output_scale: 5,
11188                expected_output_repr: Ok(99999000),
11189            },
11190            DecimalCastTestConfig {
11191                input_prec: 5,
11192                input_scale: -2,
11193                input_repr: -99999,
11194                output_prec: 10,
11195                output_scale: 3,
11196                expected_output_repr: Ok(-9999900000),
11197            },
11198            DecimalCastTestConfig {
11199                input_prec: 5,
11200                input_scale: 3,
11201                input_repr: -12345,
11202                output_prec: 6,
11203                output_scale: 5,
11204                expected_output_repr: Err("Invalid argument error: -12.34500 is too small to store in a {} of precision 6. Min is -9.99999".to_string())
11205            },
11206        ];
11207
11208        for t in test_cases {
11209            run_decimal_cast_test_case_between_multiple_types(t);
11210        }
11211    }
11212
11213    #[test]
11214    fn test_decimal_to_decimal_decrease_scale_and_precision_unchecked() {
11215        let test_cases = [
11216            DecimalCastTestConfig {
11217                input_prec: 5,
11218                input_scale: 0,
11219                input_repr: 99999,
11220                output_scale: -3,
11221                output_prec: 3,
11222                expected_output_repr: Ok(100),
11223            },
11224            DecimalCastTestConfig {
11225                input_prec: 5,
11226                input_scale: 0,
11227                input_repr: -99999,
11228                output_prec: 1,
11229                output_scale: -5,
11230                expected_output_repr: Ok(-1),
11231            },
11232            DecimalCastTestConfig {
11233                input_prec: 10,
11234                input_scale: 2,
11235                input_repr: 123456789,
11236                output_prec: 5,
11237                output_scale: -2,
11238                expected_output_repr: Ok(12346),
11239            },
11240            DecimalCastTestConfig {
11241                input_prec: 10,
11242                input_scale: 4,
11243                input_repr: -9876543210,
11244                output_prec: 7,
11245                output_scale: 0,
11246                expected_output_repr: Ok(-987654),
11247            },
11248            DecimalCastTestConfig {
11249                input_prec: 7,
11250                input_scale: 4,
11251                input_repr: 9999999,
11252                output_prec: 6,
11253                output_scale: 3,
11254                expected_output_repr:
11255                    Err("Invalid argument error: 1000.000 is too large to store in a {} of precision 6. Max is 999.999".to_string()),
11256            },
11257        ];
11258        for t in test_cases {
11259            run_decimal_cast_test_case_between_multiple_types(t);
11260        }
11261    }
11262
11263    #[test]
11264    fn test_decimal_to_decimal_throw_error_on_precision_overflow_same_scale() {
11265        let array = vec![Some(123456789)];
11266        let array = create_decimal128_array(array, 24, 2).unwrap();
11267        let input_type = DataType::Decimal128(24, 2);
11268        let output_type = DataType::Decimal128(6, 2);
11269        assert!(can_cast_types(&input_type, &output_type));
11270
11271        let options = CastOptions {
11272            safe: false,
11273            ..Default::default()
11274        };
11275        let result = cast_with_options(&array, &output_type, &options);
11276        assert_eq!(
11277            result.unwrap_err().to_string(),
11278            "Invalid argument error: 1234567.89 is too large to store in a Decimal128 of precision 6. Max is 9999.99"
11279        );
11280    }
11281
11282    #[test]
11283    fn test_decimal_to_decimal_same_scale() {
11284        let array = vec![Some(520)];
11285        let array = create_decimal128_array(array, 4, 2).unwrap();
11286        let input_type = DataType::Decimal128(4, 2);
11287        let output_type = DataType::Decimal128(3, 2);
11288        assert!(can_cast_types(&input_type, &output_type));
11289
11290        let options = CastOptions {
11291            safe: false,
11292            ..Default::default()
11293        };
11294        let result = cast_with_options(&array, &output_type, &options);
11295        assert_eq!(
11296            result.unwrap().as_primitive::<Decimal128Type>().value(0),
11297            520
11298        );
11299
11300        // Cast 0 of decimal(3, 0) type to decimal(2, 0)
11301        assert_eq!(
11302            &cast(
11303                &create_decimal128_array(vec![Some(0)], 3, 0).unwrap(),
11304                &DataType::Decimal128(2, 0)
11305            )
11306            .unwrap(),
11307            &(Arc::new(create_decimal128_array(vec![Some(0)], 2, 0).unwrap()) as ArrayRef)
11308        );
11309    }
11310
11311    #[test]
11312    fn test_decimal_to_decimal_throw_error_on_precision_overflow_lower_scale() {
11313        let array = vec![Some(123456789)];
11314        let array = create_decimal128_array(array, 24, 4).unwrap();
11315        let input_type = DataType::Decimal128(24, 4);
11316        let output_type = DataType::Decimal128(6, 2);
11317        assert!(can_cast_types(&input_type, &output_type));
11318
11319        let options = CastOptions {
11320            safe: false,
11321            ..Default::default()
11322        };
11323        let result = cast_with_options(&array, &output_type, &options);
11324        assert_eq!(
11325            result.unwrap_err().to_string(),
11326            "Invalid argument error: 12345.68 is too large to store in a Decimal128 of precision 6. Max is 9999.99"
11327        );
11328    }
11329
11330    #[test]
11331    fn test_decimal_to_decimal_throw_error_on_precision_overflow_greater_scale() {
11332        let array = vec![Some(123456789)];
11333        let array = create_decimal128_array(array, 24, 2).unwrap();
11334        let input_type = DataType::Decimal128(24, 2);
11335        let output_type = DataType::Decimal128(6, 3);
11336        assert!(can_cast_types(&input_type, &output_type));
11337
11338        let options = CastOptions {
11339            safe: false,
11340            ..Default::default()
11341        };
11342        let result = cast_with_options(&array, &output_type, &options);
11343        assert_eq!(
11344            result.unwrap_err().to_string(),
11345            "Invalid argument error: 1234567.890 is too large to store in a Decimal128 of precision 6. Max is 999.999"
11346        );
11347    }
11348
11349    #[test]
11350    fn test_decimal_to_decimal_throw_error_on_precision_overflow_diff_type() {
11351        let array = vec![Some(123456789)];
11352        let array = create_decimal128_array(array, 24, 2).unwrap();
11353        let input_type = DataType::Decimal128(24, 2);
11354        let output_type = DataType::Decimal256(6, 2);
11355        assert!(can_cast_types(&input_type, &output_type));
11356
11357        let options = CastOptions {
11358            safe: false,
11359            ..Default::default()
11360        };
11361        let result = cast_with_options(&array, &output_type, &options).unwrap_err();
11362        assert_eq!(
11363            result.to_string(),
11364            "Invalid argument error: 1234567.89 is too large to store in a Decimal256 of precision 6. Max is 9999.99"
11365        );
11366    }
11367
11368    #[test]
11369    fn test_first_none() {
11370        let array = Arc::new(ListArray::from_iter_primitive::<Int64Type, _, _>(vec![
11371            None,
11372            Some(vec![Some(1), Some(2)]),
11373        ])) as ArrayRef;
11374        let data_type =
11375            DataType::FixedSizeList(FieldRef::new(Field::new("item", DataType::Int64, true)), 2);
11376        let opt = CastOptions::default();
11377        let r = cast_with_options(&array, &data_type, &opt).unwrap();
11378
11379        let fixed_array = Arc::new(FixedSizeListArray::from_iter_primitive::<Int64Type, _, _>(
11380            vec![None, Some(vec![Some(1), Some(2)])],
11381            2,
11382        )) as ArrayRef;
11383        assert_eq!(*fixed_array, *r);
11384    }
11385
11386    #[test]
11387    fn test_first_last_none() {
11388        let array = Arc::new(ListArray::from_iter_primitive::<Int64Type, _, _>(vec![
11389            None,
11390            Some(vec![Some(1), Some(2)]),
11391            None,
11392        ])) as ArrayRef;
11393        let data_type =
11394            DataType::FixedSizeList(FieldRef::new(Field::new("item", DataType::Int64, true)), 2);
11395        let opt = CastOptions::default();
11396        let r = cast_with_options(&array, &data_type, &opt).unwrap();
11397
11398        let fixed_array = Arc::new(FixedSizeListArray::from_iter_primitive::<Int64Type, _, _>(
11399            vec![None, Some(vec![Some(1), Some(2)]), None],
11400            2,
11401        )) as ArrayRef;
11402        assert_eq!(*fixed_array, *r);
11403    }
11404
11405    #[test]
11406    fn test_cast_decimal_error_output() {
11407        let array = Int64Array::from(vec![1]);
11408        let error = cast_with_options(
11409            &array,
11410            &DataType::Decimal32(1, 1),
11411            &CastOptions {
11412                safe: false,
11413                format_options: FormatOptions::default(),
11414            },
11415        )
11416        .unwrap_err();
11417        assert_eq!(
11418            error.to_string(),
11419            "Invalid argument error: 1.0 is too large to store in a Decimal32 of precision 1. Max is 0.9"
11420        );
11421
11422        let array = Int64Array::from(vec![-1]);
11423        let error = cast_with_options(
11424            &array,
11425            &DataType::Decimal32(1, 1),
11426            &CastOptions {
11427                safe: false,
11428                format_options: FormatOptions::default(),
11429            },
11430        )
11431        .unwrap_err();
11432        assert_eq!(
11433            error.to_string(),
11434            "Invalid argument error: -1.0 is too small to store in a Decimal32 of precision 1. Min is -0.9"
11435        );
11436    }
11437
11438    #[test]
11439    fn test_run_end_encoded_to_primitive() {
11440        // Create a RunEndEncoded array: [1, 1, 2, 2, 2, 3]
11441        let run_ends = Int32Array::from(vec![2, 5, 6]);
11442        let values = Int32Array::from(vec![1, 2, 3]);
11443        let run_array = RunArray::<Int32Type>::try_new(&run_ends, &values).unwrap();
11444        let array_ref = Arc::new(run_array) as ArrayRef;
11445        // Cast to Int64
11446        let cast_result = cast(&array_ref, &DataType::Int64).unwrap();
11447        // Verify the result is a RunArray with Int64 values
11448        let result_run_array = cast_result.as_any().downcast_ref::<Int64Array>().unwrap();
11449        assert_eq!(
11450            result_run_array.values(),
11451            &[1i64, 1i64, 2i64, 2i64, 2i64, 3i64]
11452        );
11453    }
11454
11455    #[test]
11456    fn test_sliced_run_end_encoded_to_primitive() {
11457        let run_ends = Int32Array::from(vec![2, 5, 6]);
11458        let values = Int32Array::from(vec![1, 2, 3]);
11459        // [1, 1, 2, 2, 2, 3]
11460        let run_array = RunArray::<Int32Type>::try_new(&run_ends, &values).unwrap();
11461        let run_array = run_array.slice(3, 3); // [2, 2, 3]
11462        let array_ref = Arc::new(run_array) as ArrayRef;
11463
11464        let cast_result = cast(&array_ref, &DataType::Int64).unwrap();
11465        let result_run_array = cast_result.as_primitive::<Int64Type>();
11466        assert_eq!(result_run_array.values(), &[2, 2, 3]);
11467    }
11468
11469    #[test]
11470    fn test_run_end_encoded_to_string() {
11471        let run_ends = Int32Array::from(vec![2, 3, 5]);
11472        let values = Int32Array::from(vec![10, 20, 30]);
11473        let run_array = RunArray::<Int32Type>::try_new(&run_ends, &values).unwrap();
11474        let array_ref = Arc::new(run_array) as ArrayRef;
11475
11476        // Cast to String
11477        let cast_result = cast(&array_ref, &DataType::Utf8).unwrap();
11478
11479        // Verify the result is a RunArray with String values
11480        let result_array = cast_result.as_any().downcast_ref::<StringArray>().unwrap();
11481        // Check that values are correct
11482        assert_eq!(result_array.value(0), "10");
11483        assert_eq!(result_array.value(1), "10");
11484        assert_eq!(result_array.value(2), "20");
11485    }
11486
11487    #[test]
11488    fn test_primitive_to_run_end_encoded() {
11489        // Create an Int32 array with repeated values: [1, 1, 2, 2, 2, 3]
11490        let source_array = Int32Array::from(vec![1, 1, 2, 2, 2, 3]);
11491        let array_ref = Arc::new(source_array) as ArrayRef;
11492
11493        // Cast to RunEndEncoded<Int32, Int32>
11494        let target_type = DataType::RunEndEncoded(
11495            Arc::new(Field::new(
11496                Field::REE_RUN_ENDS_FIELD_DEFAULT_NAME,
11497                DataType::Int32,
11498                false,
11499            )),
11500            Arc::new(Field::new(
11501                Field::REE_VALUES_FIELD_DEFAULT_NAME,
11502                DataType::Int32,
11503                true,
11504            )),
11505        );
11506        let cast_result = cast(&array_ref, &target_type).unwrap();
11507
11508        // Verify the result is a RunArray
11509        let result_run_array = cast_result
11510            .as_any()
11511            .downcast_ref::<RunArray<Int32Type>>()
11512            .unwrap();
11513
11514        // Check run structure: runs should end at positions [2, 5, 6]
11515        assert_eq!(result_run_array.run_ends().values(), &[2, 5, 6]);
11516
11517        // Check values: should be [1, 2, 3]
11518        let values_array = result_run_array.values().as_primitive::<Int32Type>();
11519        assert_eq!(values_array.values(), &[1, 2, 3]);
11520    }
11521
11522    #[test]
11523    fn test_primitive_to_run_end_encoded_with_nulls() {
11524        let source_array = Int32Array::from(vec![
11525            Some(1),
11526            Some(1),
11527            None,
11528            None,
11529            Some(2),
11530            Some(2),
11531            Some(3),
11532            Some(3),
11533            None,
11534            None,
11535            Some(4),
11536            Some(4),
11537            Some(5),
11538            Some(5),
11539            None,
11540            None,
11541        ]);
11542        let array_ref = Arc::new(source_array) as ArrayRef;
11543        let target_type = DataType::RunEndEncoded(
11544            Arc::new(Field::new(
11545                Field::REE_RUN_ENDS_FIELD_DEFAULT_NAME,
11546                DataType::Int32,
11547                false,
11548            )),
11549            Arc::new(Field::new(
11550                Field::REE_VALUES_FIELD_DEFAULT_NAME,
11551                DataType::Int32,
11552                true,
11553            )),
11554        );
11555        let cast_result = cast(&array_ref, &target_type).unwrap();
11556        let result_run_array = cast_result
11557            .as_any()
11558            .downcast_ref::<RunArray<Int32Type>>()
11559            .unwrap();
11560        assert_eq!(
11561            result_run_array.run_ends().values(),
11562            &[2, 4, 6, 8, 10, 12, 14, 16]
11563        );
11564        assert_eq!(
11565            result_run_array
11566                .values()
11567                .as_primitive::<Int32Type>()
11568                .values(),
11569            &[1, 0, 2, 3, 0, 4, 5, 0]
11570        );
11571        assert_eq!(result_run_array.values().null_count(), 3);
11572    }
11573
11574    #[test]
11575    fn test_primitive_to_run_end_encoded_with_nulls_consecutive() {
11576        let source_array = Int64Array::from(vec![
11577            Some(1),
11578            Some(1),
11579            None,
11580            None,
11581            None,
11582            None,
11583            None,
11584            None,
11585            None,
11586            None,
11587            Some(4),
11588            Some(20),
11589            Some(500),
11590            Some(500),
11591            None,
11592            None,
11593        ]);
11594        let array_ref = Arc::new(source_array) as ArrayRef;
11595        let target_type = DataType::RunEndEncoded(
11596            Arc::new(Field::new(
11597                Field::REE_RUN_ENDS_FIELD_DEFAULT_NAME,
11598                DataType::Int16,
11599                false,
11600            )),
11601            Arc::new(Field::new(
11602                Field::REE_VALUES_FIELD_DEFAULT_NAME,
11603                DataType::Int64,
11604                true,
11605            )),
11606        );
11607        let cast_result = cast(&array_ref, &target_type).unwrap();
11608        let result_run_array = cast_result
11609            .as_any()
11610            .downcast_ref::<RunArray<Int16Type>>()
11611            .unwrap();
11612        assert_eq!(
11613            result_run_array.run_ends().values(),
11614            &[2, 10, 11, 12, 14, 16]
11615        );
11616        assert_eq!(
11617            result_run_array
11618                .values()
11619                .as_primitive::<Int64Type>()
11620                .values(),
11621            &[1, 0, 4, 20, 500, 0]
11622        );
11623        assert_eq!(result_run_array.values().null_count(), 2);
11624    }
11625
11626    #[test]
11627    fn test_string_to_run_end_encoded() {
11628        // Create a String array with repeated values: ["a", "a", "b", "c", "c"]
11629        let source_array = StringArray::from(vec!["a", "a", "b", "c", "c"]);
11630        let array_ref = Arc::new(source_array) as ArrayRef;
11631
11632        // Cast to RunEndEncoded<Int32, String>
11633        let target_type = DataType::RunEndEncoded(
11634            Arc::new(Field::new(
11635                Field::REE_RUN_ENDS_FIELD_DEFAULT_NAME,
11636                DataType::Int32,
11637                false,
11638            )),
11639            Arc::new(Field::new(
11640                Field::REE_VALUES_FIELD_DEFAULT_NAME,
11641                DataType::Utf8,
11642                true,
11643            )),
11644        );
11645        let cast_result = cast(&array_ref, &target_type).unwrap();
11646
11647        // Verify the result is a RunArray
11648        let result_run_array = cast_result
11649            .as_any()
11650            .downcast_ref::<RunArray<Int32Type>>()
11651            .unwrap();
11652
11653        // Check run structure: runs should end at positions [2, 3, 5]
11654        assert_eq!(result_run_array.run_ends().values(), &[2, 3, 5]);
11655
11656        // Check values: should be ["a", "b", "c"]
11657        let values_array = result_run_array.values().as_string::<i32>();
11658        assert_eq!(values_array.value(0), "a");
11659        assert_eq!(values_array.value(1), "b");
11660        assert_eq!(values_array.value(2), "c");
11661    }
11662
11663    #[test]
11664    fn test_empty_array_to_run_end_encoded() {
11665        // Create an empty Int32 array
11666        let source_array = Int32Array::from(Vec::<i32>::new());
11667        let array_ref = Arc::new(source_array) as ArrayRef;
11668
11669        // Cast to RunEndEncoded<Int32, Int32>
11670        let target_type = DataType::RunEndEncoded(
11671            Arc::new(Field::new(
11672                Field::REE_RUN_ENDS_FIELD_DEFAULT_NAME,
11673                DataType::Int32,
11674                false,
11675            )),
11676            Arc::new(Field::new(
11677                Field::REE_VALUES_FIELD_DEFAULT_NAME,
11678                DataType::Int32,
11679                true,
11680            )),
11681        );
11682        let cast_result = cast(&array_ref, &target_type).unwrap();
11683
11684        // Verify the result is an empty RunArray
11685        let result_run_array = cast_result
11686            .as_any()
11687            .downcast_ref::<RunArray<Int32Type>>()
11688            .unwrap();
11689
11690        // Check that both run_ends and values are empty
11691        assert_eq!(result_run_array.run_ends().len(), 0);
11692        assert_eq!(result_run_array.values().len(), 0);
11693    }
11694
11695    #[test]
11696    fn test_run_end_encoded_with_nulls() {
11697        // Create a RunEndEncoded array with nulls: [1, 1, null, 2, 2]
11698        let run_ends = Int32Array::from(vec![2, 3, 5]);
11699        let values = Int32Array::from(vec![Some(1), None, Some(2)]);
11700        let run_array = RunArray::<Int32Type>::try_new(&run_ends, &values).unwrap();
11701        let array_ref = Arc::new(run_array) as ArrayRef;
11702
11703        // Cast to String
11704        let cast_result = cast(&array_ref, &DataType::Utf8).unwrap();
11705
11706        // Verify the result preserves nulls
11707        let result_run_array = cast_result.as_any().downcast_ref::<StringArray>().unwrap();
11708        assert_eq!(result_run_array.value(0), "1");
11709        assert!(result_run_array.is_null(2));
11710        assert_eq!(result_run_array.value(4), "2");
11711    }
11712
11713    #[test]
11714    fn test_different_index_types() {
11715        // Test with Int16 index type
11716        let source_array = Int32Array::from(vec![1, 1, 2, 3, 3]);
11717        let array_ref = Arc::new(source_array) as ArrayRef;
11718
11719        let target_type = DataType::RunEndEncoded(
11720            Arc::new(Field::new(
11721                Field::REE_RUN_ENDS_FIELD_DEFAULT_NAME,
11722                DataType::Int16,
11723                false,
11724            )),
11725            Arc::new(Field::new(
11726                Field::REE_VALUES_FIELD_DEFAULT_NAME,
11727                DataType::Int32,
11728                true,
11729            )),
11730        );
11731        let cast_result = cast(&array_ref, &target_type).unwrap();
11732        assert_eq!(cast_result.data_type(), &target_type);
11733
11734        // Verify the cast worked correctly: values are [1, 2, 3]
11735        // and run-ends are [2, 3, 5]
11736        let run_array = cast_result
11737            .as_any()
11738            .downcast_ref::<RunArray<Int16Type>>()
11739            .unwrap();
11740        assert_eq!(run_array.values().as_primitive::<Int32Type>().value(0), 1);
11741        assert_eq!(run_array.values().as_primitive::<Int32Type>().value(1), 2);
11742        assert_eq!(run_array.values().as_primitive::<Int32Type>().value(2), 3);
11743        assert_eq!(run_array.run_ends().values(), &[2i16, 3i16, 5i16]);
11744
11745        // Test again with Int64 index type
11746        let target_type = DataType::RunEndEncoded(
11747            Arc::new(Field::new(
11748                Field::REE_RUN_ENDS_FIELD_DEFAULT_NAME,
11749                DataType::Int64,
11750                false,
11751            )),
11752            Arc::new(Field::new(
11753                Field::REE_VALUES_FIELD_DEFAULT_NAME,
11754                DataType::Int32,
11755                true,
11756            )),
11757        );
11758        let cast_result = cast(&array_ref, &target_type).unwrap();
11759        assert_eq!(cast_result.data_type(), &target_type);
11760
11761        // Verify the cast worked correctly: values are [1, 2, 3]
11762        // and run-ends are [2, 3, 5]
11763        let run_array = cast_result
11764            .as_any()
11765            .downcast_ref::<RunArray<Int64Type>>()
11766            .unwrap();
11767        assert_eq!(run_array.values().as_primitive::<Int32Type>().value(0), 1);
11768        assert_eq!(run_array.values().as_primitive::<Int32Type>().value(1), 2);
11769        assert_eq!(run_array.values().as_primitive::<Int32Type>().value(2), 3);
11770        assert_eq!(run_array.run_ends().values(), &[2i64, 3i64, 5i64]);
11771    }
11772
11773    #[test]
11774    fn test_unsupported_cast_to_run_end_encoded() {
11775        // Create a Struct array - complex nested type that might not be supported
11776        let field = Field::new("item", DataType::Int32, false);
11777        let struct_array = StructArray::from(vec![(
11778            Arc::new(field),
11779            Arc::new(Int32Array::from(vec![1, 2, 3])) as ArrayRef,
11780        )]);
11781        let array_ref = Arc::new(struct_array) as ArrayRef;
11782
11783        // This should fail because:
11784        // 1. The target type is not RunEndEncoded
11785        // 2. The target type is not supported for casting from StructArray
11786        let cast_result = cast(&array_ref, &DataType::FixedSizeBinary(10));
11787
11788        // Expect this to fail
11789        assert!(cast_result.is_err());
11790    }
11791
11792    /// Test casting RunEndEncoded<Int64, String> to RunEndEncoded<Int16, String> should fail
11793    #[test]
11794    fn test_cast_run_end_encoded_int64_to_int16_should_fail() {
11795        // Construct a valid REE array with Int64 run-ends
11796        let run_ends = Int64Array::from(vec![100_000, 400_000, 700_000]); // values too large for Int16
11797        let values = StringArray::from(vec!["a", "b", "c"]);
11798
11799        let ree_array = RunArray::<Int64Type>::try_new(&run_ends, &values).unwrap();
11800        let array_ref = Arc::new(ree_array) as ArrayRef;
11801
11802        // Attempt to cast to RunEndEncoded<Int16, Utf8>
11803        let target_type = DataType::RunEndEncoded(
11804            Arc::new(Field::new(
11805                Field::REE_RUN_ENDS_FIELD_DEFAULT_NAME,
11806                DataType::Int16,
11807                false,
11808            )),
11809            Arc::new(Field::new(
11810                Field::REE_VALUES_FIELD_DEFAULT_NAME,
11811                DataType::Utf8,
11812                true,
11813            )),
11814        );
11815        let cast_options = CastOptions {
11816            safe: false, // This should make it fail instead of returning nulls
11817            format_options: FormatOptions::default(),
11818        };
11819
11820        // This should fail due to run-end overflow
11821        let result: Result<Arc<dyn Array + 'static>, ArrowError> =
11822            cast_with_options(&array_ref, &target_type, &cast_options);
11823
11824        let e = result.expect_err("Cast should have failed but succeeded");
11825        assert!(
11826            e.to_string()
11827                .contains("Cast error: Can't cast value 100000 to type Int16")
11828        );
11829    }
11830
11831    #[test]
11832    fn test_cast_run_end_encoded_int64_to_int16_with_safe_should_fail_with_null_invalid_error() {
11833        // Construct a valid REE array with Int64 run-ends
11834        let run_ends = Int64Array::from(vec![100_000, 400_000, 700_000]); // values too large for Int16
11835        let values = StringArray::from(vec!["a", "b", "c"]);
11836
11837        let ree_array = RunArray::<Int64Type>::try_new(&run_ends, &values).unwrap();
11838        let array_ref = Arc::new(ree_array) as ArrayRef;
11839
11840        // Attempt to cast to RunEndEncoded<Int16, Utf8>
11841        let target_type = DataType::RunEndEncoded(
11842            Arc::new(Field::new(
11843                Field::REE_RUN_ENDS_FIELD_DEFAULT_NAME,
11844                DataType::Int16,
11845                false,
11846            )),
11847            Arc::new(Field::new(
11848                Field::REE_VALUES_FIELD_DEFAULT_NAME,
11849                DataType::Utf8,
11850                true,
11851            )),
11852        );
11853        let cast_options = CastOptions {
11854            safe: true,
11855            format_options: FormatOptions::default(),
11856        };
11857
11858        // This fails even though safe is true because the run_ends array has null values
11859        let result: Result<Arc<dyn Array + 'static>, ArrowError> =
11860            cast_with_options(&array_ref, &target_type, &cast_options);
11861        let e = result.expect_err("Cast should have failed but succeeded");
11862        assert!(
11863            e.to_string()
11864                .contains("Invalid argument error: Found null values in run_ends array. The run_ends array should not have null values.")
11865        );
11866    }
11867
11868    /// Test casting RunEndEncoded<Int16, String> to RunEndEncoded<Int64, String> should succeed
11869    #[test]
11870    fn test_cast_run_end_encoded_int16_to_int64_should_succeed() {
11871        // Construct a valid REE array with Int16 run-ends
11872        let run_ends = Int16Array::from(vec![2, 5, 8]); // values that fit in Int16
11873        let values = StringArray::from(vec!["a", "b", "c"]);
11874
11875        let ree_array = RunArray::<Int16Type>::try_new(&run_ends, &values).unwrap();
11876        let array_ref = Arc::new(ree_array) as ArrayRef;
11877
11878        // Attempt to cast to RunEndEncoded<Int64, Utf8> (upcast should succeed)
11879        let target_type = DataType::RunEndEncoded(
11880            Arc::new(Field::new(
11881                Field::REE_RUN_ENDS_FIELD_DEFAULT_NAME,
11882                DataType::Int64,
11883                false,
11884            )),
11885            Arc::new(Field::new(
11886                Field::REE_VALUES_FIELD_DEFAULT_NAME,
11887                DataType::Utf8,
11888                true,
11889            )),
11890        );
11891        let cast_options = CastOptions {
11892            safe: false,
11893            format_options: FormatOptions::default(),
11894        };
11895
11896        // This should succeed due to valid upcast
11897        let result: Result<Arc<dyn Array + 'static>, ArrowError> =
11898            cast_with_options(&array_ref, &target_type, &cast_options);
11899
11900        let array_ref = result.expect("Cast should have succeeded but failed");
11901        // Downcast to RunArray<Int64Type>
11902        let run_array = array_ref
11903            .as_any()
11904            .downcast_ref::<RunArray<Int64Type>>()
11905            .unwrap();
11906
11907        // Verify the cast worked correctly
11908        // Assert the values were cast correctly
11909        assert_eq!(run_array.run_ends().values(), &[2i64, 5i64, 8i64]);
11910        assert_eq!(run_array.values().as_string::<i32>().value(0), "a");
11911        assert_eq!(run_array.values().as_string::<i32>().value(1), "b");
11912        assert_eq!(run_array.values().as_string::<i32>().value(2), "c");
11913    }
11914
11915    #[test]
11916    fn test_cast_run_end_encoded_dictionary_to_run_end_encoded() {
11917        // Construct a valid dictionary encoded array
11918        let values = StringArray::from_iter([Some("a"), Some("b"), Some("c")]);
11919        let keys = UInt64Array::from_iter(vec![1, 1, 1, 0, 0, 0, 2, 2, 2]);
11920        let array_ref = Arc::new(DictionaryArray::new(keys, Arc::new(values))) as ArrayRef;
11921
11922        // Attempt to cast to RunEndEncoded<Int64, Utf8>
11923        let target_type = DataType::RunEndEncoded(
11924            Arc::new(Field::new(
11925                Field::REE_RUN_ENDS_FIELD_DEFAULT_NAME,
11926                DataType::Int64,
11927                false,
11928            )),
11929            Arc::new(Field::new(
11930                Field::REE_VALUES_FIELD_DEFAULT_NAME,
11931                DataType::Utf8,
11932                true,
11933            )),
11934        );
11935        let cast_options = CastOptions {
11936            safe: false,
11937            format_options: FormatOptions::default(),
11938        };
11939
11940        // This should succeed
11941        let result = cast_with_options(&array_ref, &target_type, &cast_options)
11942            .expect("Cast should have succeeded but failed");
11943
11944        // Verify the cast worked correctly
11945        // Assert the values were cast correctly
11946        let run_array = result
11947            .as_any()
11948            .downcast_ref::<RunArray<Int64Type>>()
11949            .unwrap();
11950        assert_eq!(run_array.values().as_string::<i32>().value(0), "b");
11951        assert_eq!(run_array.values().as_string::<i32>().value(1), "a");
11952        assert_eq!(run_array.values().as_string::<i32>().value(2), "c");
11953
11954        // Verify the run-ends were cast correctly (run ends at 3, 6, 9)
11955        assert_eq!(run_array.run_ends().values(), &[3i64, 6i64, 9i64]);
11956    }
11957
11958    #[test]
11959    fn test_cast_time32_second_to_int64() {
11960        let array = Time32SecondArray::from(vec![1000, 2000, 3000]);
11961        let array = Arc::new(array) as Arc<dyn Array>;
11962        let to_type = DataType::Int64;
11963        let cast_options = CastOptions::default();
11964
11965        assert!(can_cast_types(array.data_type(), &to_type));
11966
11967        let result = cast_with_options(&array, &to_type, &cast_options);
11968        assert!(
11969            result.is_ok(),
11970            "Failed to cast Time32(Second) to Int64: {:?}",
11971            result.err()
11972        );
11973
11974        let cast_array = result.unwrap();
11975        let cast_array = cast_array.as_any().downcast_ref::<Int64Array>().unwrap();
11976
11977        assert_eq!(cast_array.value(0), 1000);
11978        assert_eq!(cast_array.value(1), 2000);
11979        assert_eq!(cast_array.value(2), 3000);
11980    }
11981
11982    #[test]
11983    fn test_cast_time32_millisecond_to_int64() {
11984        let array = Time32MillisecondArray::from(vec![1000, 2000, 3000]);
11985        let array = Arc::new(array) as Arc<dyn Array>;
11986        let to_type = DataType::Int64;
11987        let cast_options = CastOptions::default();
11988
11989        assert!(can_cast_types(array.data_type(), &to_type));
11990
11991        let result = cast_with_options(&array, &to_type, &cast_options);
11992        assert!(
11993            result.is_ok(),
11994            "Failed to cast Time32(Millisecond) to Int64: {:?}",
11995            result.err()
11996        );
11997
11998        let cast_array = result.unwrap();
11999        let cast_array = cast_array.as_any().downcast_ref::<Int64Array>().unwrap();
12000
12001        assert_eq!(cast_array.value(0), 1000);
12002        assert_eq!(cast_array.value(1), 2000);
12003        assert_eq!(cast_array.value(2), 3000);
12004    }
12005
12006    #[test]
12007    fn test_cast_time32_millisecond_to_time64_nanosecond() {
12008        let array =
12009            Time32MillisecondArray::from(vec![Some(1_000), Some(2_000), None, Some(43_200_000)]);
12010        let b = cast(&array, &DataType::Time64(TimeUnit::Nanosecond)).unwrap();
12011        let c = b.as_primitive::<Time64NanosecondType>();
12012        assert_eq!(c.value(0), 1_000_000_000);
12013        assert_eq!(c.value(1), 2_000_000_000);
12014        assert!(c.is_null(2));
12015        assert_eq!(c.value(3), 43_200_000_000_000);
12016    }
12017
12018    #[test]
12019    fn test_cast_time32_millisecond_to_time64_microsecond() {
12020        let array =
12021            Time32MillisecondArray::from(vec![Some(1_000), Some(2_000), None, Some(43_200_000)]);
12022        let b = cast(&array, &DataType::Time64(TimeUnit::Microsecond)).unwrap();
12023        let c = b.as_primitive::<Time64MicrosecondType>();
12024        assert_eq!(c.value(0), 1_000_000);
12025        assert_eq!(c.value(1), 2_000_000);
12026        assert!(c.is_null(2));
12027        assert_eq!(c.value(3), 43_200_000_000);
12028    }
12029
12030    #[test]
12031    fn test_cast_time32_second_to_time64_nanosecond() {
12032        let array = Time32SecondArray::from(vec![Some(1), Some(60), None, Some(43_200)]);
12033        let b = cast(&array, &DataType::Time64(TimeUnit::Nanosecond)).unwrap();
12034        let c = b.as_primitive::<Time64NanosecondType>();
12035        assert_eq!(c.value(0), 1_000_000_000);
12036        assert_eq!(c.value(1), 60_000_000_000);
12037        assert!(c.is_null(2));
12038        assert_eq!(c.value(3), 43_200_000_000_000);
12039    }
12040
12041    #[test]
12042    fn test_cast_time32_second_to_time64_microsecond() {
12043        let array = Time32SecondArray::from(vec![Some(1), Some(60), None, Some(43_200)]);
12044        let b = cast(&array, &DataType::Time64(TimeUnit::Microsecond)).unwrap();
12045        let c = b.as_primitive::<Time64MicrosecondType>();
12046        assert_eq!(c.value(0), 1_000_000);
12047        assert_eq!(c.value(1), 60_000_000);
12048        assert!(c.is_null(2));
12049        assert_eq!(c.value(3), 43_200_000_000);
12050    }
12051
12052    #[test]
12053    fn test_cast_time32_second_to_time32_millisecond_overflow() {
12054        let array = Time32SecondArray::from(vec![i32::MAX]);
12055
12056        let b = cast(&array, &DataType::Time32(TimeUnit::Millisecond)).unwrap();
12057        let c = b.as_primitive::<Time32MillisecondType>();
12058        assert!(c.is_null(0));
12059
12060        let options = CastOptions {
12061            safe: false,
12062            ..Default::default()
12063        };
12064        let err = cast_with_options(&array, &DataType::Time32(TimeUnit::Millisecond), &options)
12065            .unwrap_err();
12066        assert!(err.to_string().contains("Overflow"), "{err}");
12067    }
12068
12069    fn assert_temporal_overflow_is_safe(array: &dyn Array, to_type: &DataType) {
12070        let result = cast(array, to_type).unwrap();
12071        assert_eq!(result.null_count(), array.len());
12072
12073        let options = CastOptions {
12074            safe: false,
12075            ..Default::default()
12076        };
12077        assert!(cast_with_options(array, to_type, &options).is_err());
12078    }
12079
12080    #[test]
12081    fn test_cast_time64_overflow() {
12082        let microseconds = Time64MicrosecondArray::from(vec![i64::MIN, i64::MAX]);
12083        for to_type in [
12084            DataType::Time32(TimeUnit::Second),
12085            DataType::Time32(TimeUnit::Millisecond),
12086            DataType::Time64(TimeUnit::Nanosecond),
12087        ] {
12088            assert_temporal_overflow_is_safe(&microseconds, &to_type);
12089        }
12090
12091        let nanoseconds = Time64NanosecondArray::from(vec![i64::MIN, i64::MAX]);
12092        for to_type in [
12093            DataType::Time32(TimeUnit::Second),
12094            DataType::Time32(TimeUnit::Millisecond),
12095        ] {
12096            assert_temporal_overflow_is_safe(&nanoseconds, &to_type);
12097        }
12098    }
12099
12100    #[test]
12101    fn test_cast_date64_to_timestamp_overflow() {
12102        let array = Date64Array::from(vec![i64::MIN, i64::MAX]);
12103        for to_type in [
12104            DataType::Timestamp(TimeUnit::Microsecond, None),
12105            DataType::Timestamp(TimeUnit::Nanosecond, None),
12106        ] {
12107            assert_temporal_overflow_is_safe(&array, &to_type);
12108        }
12109    }
12110
12111    #[test]
12112    fn test_cast_time64_to_time32_boundaries() {
12113        fn check<FROM, TO>(divisor: i64)
12114        where
12115            FROM: ArrowPrimitiveType<Native = i64>,
12116            TO: ArrowPrimitiveType<Native = i32>,
12117        {
12118            // Division truncates towards zero before the range check. Values
12119            // slightly outside the scaled i32 bounds can still be representable.
12120            let min = <i64 as From<i32>>::from(i32::MIN) * divisor - (divisor - 1);
12121            let max = <i64 as From<i32>>::from(i32::MAX) * divisor + (divisor - 1);
12122            let array = PrimitiveArray::<FROM>::new(
12123                vec![i64::MAX, min - 1, min, -divisor + 1, i64::MAX, max, max + 1].into(),
12124                Some(vec![true, true, true, true, false, true, true].into()),
12125            )
12126            .slice(1, 6);
12127            let expected = PrimitiveArray::<TO>::from_iter([
12128                None,
12129                Some(i32::MIN),
12130                Some(0),
12131                None,
12132                Some(i32::MAX),
12133                None,
12134            ]);
12135            let result = cast(&array, &TO::DATA_TYPE).unwrap();
12136            assert_eq!(result.as_primitive::<TO>(), &expected);
12137
12138            let options = CastOptions {
12139                safe: false,
12140                ..Default::default()
12141            };
12142            assert!(cast_with_options(&array, &TO::DATA_TYPE, &options).is_err());
12143            // The invalid physical value under the null must not cause an error.
12144            let result = cast_with_options(&array.slice(1, 4), &TO::DATA_TYPE, &options).unwrap();
12145            assert_eq!(result.as_primitive::<TO>(), &expected.slice(1, 4));
12146        }
12147        check::<Time64MicrosecondType, Time32SecondType>(MICROSECONDS);
12148        check::<Time64MicrosecondType, Time32MillisecondType>(MICROSECONDS / MILLISECONDS);
12149        check::<Time64NanosecondType, Time32SecondType>(NANOSECONDS);
12150        check::<Time64NanosecondType, Time32MillisecondType>(NANOSECONDS / MILLISECONDS);
12151    }
12152
12153    #[test]
12154    fn test_cast_temporal_scaling_boundaries() {
12155        fn check<FROM, TO>(multiplier: i64)
12156        where
12157            FROM: ArrowPrimitiveType<Native = i64>,
12158            TO: ArrowPrimitiveType<Native = i64>,
12159        {
12160            let min = i64::MIN / multiplier;
12161            let max = i64::MAX / multiplier;
12162            let array = PrimitiveArray::<FROM>::new(
12163                vec![i64::MAX, min - 1, min, -1, i64::MAX, max, max + 1].into(),
12164                Some(vec![true, true, true, true, false, true, true].into()),
12165            )
12166            .slice(1, 6);
12167            let expected = PrimitiveArray::<TO>::from_iter([
12168                None,
12169                Some(min * multiplier),
12170                Some(-multiplier),
12171                None,
12172                Some(max * multiplier),
12173                None,
12174            ]);
12175            let result = cast(&array, &TO::DATA_TYPE).unwrap();
12176            assert_eq!(result.as_primitive::<TO>(), &expected);
12177            let options = CastOptions {
12178                safe: false,
12179                ..Default::default()
12180            };
12181            assert!(cast_with_options(&array, &TO::DATA_TYPE, &options).is_err());
12182            let result = cast_with_options(&array.slice(1, 4), &TO::DATA_TYPE, &options).unwrap();
12183            assert_eq!(result.as_primitive::<TO>(), &expected.slice(1, 4));
12184        }
12185        check::<Time64MicrosecondType, Time64NanosecondType>(NANOSECONDS / MICROSECONDS);
12186        check::<Date64Type, TimestampMicrosecondType>(MICROSECONDS / MILLISECONDS);
12187        check::<Date64Type, TimestampNanosecondType>(NANOSECONDS / MILLISECONDS);
12188    }
12189
12190    #[test]
12191    fn test_cast_string_to_time32_second_to_int64() {
12192        // Mimic: select arrow_cast('03:12:44'::time, 'Time32(Second)')::bigint;
12193        // raised in https://github.com/apache/datafusion/issues/19036
12194        let array = StringArray::from(vec!["03:12:44"]);
12195        let array = Arc::new(array) as Arc<dyn Array>;
12196        let cast_options = CastOptions::default();
12197
12198        // 1. Cast String to Time32(Second)
12199        let time32_type = DataType::Time32(TimeUnit::Second);
12200        let time32_array = cast_with_options(&array, &time32_type, &cast_options).unwrap();
12201
12202        // 2. Cast Time32(Second) to Int64
12203        let int64_type = DataType::Int64;
12204        assert!(can_cast_types(time32_array.data_type(), &int64_type));
12205
12206        let result = cast_with_options(&time32_array, &int64_type, &cast_options);
12207
12208        assert!(
12209            result.is_ok(),
12210            "Failed to cast Time32(Second) to Int64: {:?}",
12211            result.err()
12212        );
12213
12214        let cast_array = result.unwrap();
12215        let cast_array = cast_array.as_any().downcast_ref::<Int64Array>().unwrap();
12216
12217        // 03:12:44 = 3*3600 + 12*60 + 44 = 10800 + 720 + 44 = 11564
12218        assert_eq!(cast_array.value(0), 11564);
12219    }
12220    #[test]
12221    fn test_string_dicts_to_binary_view() {
12222        let expected = BinaryViewArray::from_iter(vec![
12223            VIEW_TEST_DATA[1],
12224            VIEW_TEST_DATA[0],
12225            None,
12226            VIEW_TEST_DATA[3],
12227            None,
12228            VIEW_TEST_DATA[1],
12229            VIEW_TEST_DATA[4],
12230        ]);
12231
12232        let values_arrays: [ArrayRef; _] = [
12233            Arc::new(StringArray::from_iter(VIEW_TEST_DATA)),
12234            Arc::new(StringViewArray::from_iter(VIEW_TEST_DATA)),
12235            Arc::new(LargeStringArray::from_iter(VIEW_TEST_DATA)),
12236        ];
12237        for values in values_arrays {
12238            let keys =
12239                Int8Array::from_iter([Some(1), Some(0), None, Some(3), None, Some(1), Some(4)]);
12240            let string_dict_array = DictionaryArray::<Int8Type>::try_new(keys, values).unwrap();
12241
12242            let casted = cast(&string_dict_array, &DataType::BinaryView).unwrap();
12243            assert_eq!(casted.as_ref(), &expected);
12244        }
12245    }
12246
12247    #[test]
12248    fn test_binary_dicts_to_string_view() {
12249        let expected = StringViewArray::from_iter(vec![
12250            VIEW_TEST_DATA[1],
12251            VIEW_TEST_DATA[0],
12252            None,
12253            VIEW_TEST_DATA[3],
12254            None,
12255            VIEW_TEST_DATA[1],
12256            VIEW_TEST_DATA[4],
12257        ]);
12258
12259        let values_arrays: [ArrayRef; _] = [
12260            Arc::new(BinaryArray::from_iter(VIEW_TEST_DATA)),
12261            Arc::new(BinaryViewArray::from_iter(VIEW_TEST_DATA)),
12262            Arc::new(LargeBinaryArray::from_iter(VIEW_TEST_DATA)),
12263        ];
12264        for values in values_arrays {
12265            let keys =
12266                Int8Array::from_iter([Some(1), Some(0), None, Some(3), None, Some(1), Some(4)]);
12267            let string_dict_array = DictionaryArray::<Int8Type>::try_new(keys, values).unwrap();
12268
12269            let casted = cast(&string_dict_array, &DataType::Utf8View).unwrap();
12270            assert_eq!(casted.as_ref(), &expected);
12271        }
12272    }
12273
12274    #[test]
12275    fn test_cast_between_sliced_run_end_encoded() {
12276        let run_ends = Int16Array::from(vec![2, 5, 8]);
12277        let values = StringArray::from(vec!["a", "b", "c"]);
12278
12279        let ree_array = RunArray::<Int16Type>::try_new(&run_ends, &values).unwrap();
12280        let ree_array = ree_array.slice(1, 2);
12281        let array_ref = Arc::new(ree_array) as ArrayRef;
12282
12283        let target_type = DataType::RunEndEncoded(
12284            Arc::new(Field::new(
12285                Field::REE_RUN_ENDS_FIELD_DEFAULT_NAME,
12286                DataType::Int64,
12287                false,
12288            )),
12289            Arc::new(Field::new(
12290                Field::REE_VALUES_FIELD_DEFAULT_NAME,
12291                DataType::Utf8,
12292                true,
12293            )),
12294        );
12295        let cast_options = CastOptions {
12296            safe: false,
12297            format_options: FormatOptions::default(),
12298        };
12299
12300        let result = cast_with_options(&array_ref, &target_type, &cast_options).unwrap();
12301        let run_array = result.as_run::<Int64Type>();
12302        let run_array = run_array.downcast::<StringArray>().unwrap();
12303
12304        let expected = vec!["a", "b"];
12305        let actual = run_array.into_iter().flatten().collect::<Vec<_>>();
12306
12307        assert_eq!(expected, actual);
12308    }
12309
12310    fn decimal128(unscaled: i128, precision: u8, scale: i8) -> Decimal128Array {
12311        Decimal128Array::from(vec![unscaled])
12312            .with_precision_and_scale(precision, scale)
12313            .unwrap()
12314    }
12315
12316    #[test]
12317    fn test_cast_decimal_to_float_is_correctly_rounded() {
12318        // (unscaled, scale, nearest double). The last four already passed.
12319        for (unscaled, scale, expected) in [
12320            (12345678901234567890i128, 2i8, 1.2345678901234568e17f64),
12321            (10i128.pow(37), 37, 1.0),
12322            (123456789012345678901, 20, 1.2345678901234567),
12323            (1, 37, 1e-37),
12324            (1, 1, 0.1),
12325            (15, 1, 1.5),
12326            (123456, 3, 123.456),
12327            (-123456, 3, -123.456),
12328        ] {
12329            let out = cast(&decimal128(unscaled, 38, scale), &DataType::Float64).unwrap();
12330            assert_eq!(
12331                out.as_primitive::<Float64Type>().value(0),
12332                expected,
12333                "Decimal128({unscaled}, scale={scale}) -> Float64"
12334            );
12335        }
12336
12337        // (unscaled, scale, nearest float). The first three differ from
12338        // `(f32) (f64) value`, so fixing the f64 path alone leaves them wrong.
12339        for (unscaled, scale, expected) in [
12340            (13631072500000000514758830i128, 18i8, 13631073.0f32),
12341            (72073620000000000000000582908005, 24, 72073624.0),
12342            (-3273316900000000000957536840, 20, -32733170.0),
12343            (123456, 3, 123.456),
12344            (-12345678, 3, -12345.678),
12345            (1, 10, 1e-10),
12346        ] {
12347            let out = cast(&decimal128(unscaled, 38, scale), &DataType::Float32).unwrap();
12348            assert_eq!(
12349                out.as_primitive::<Float32Type>().value(0),
12350                expected,
12351                "Decimal128({unscaled}, scale={scale}) -> Float32"
12352            );
12353        }
12354    }
12355
12356    // Both sides of every boundary the conversion switches on.
12357    #[test]
12358    fn test_cast_decimal_to_float_matches_parsing_its_own_text() {
12359        for (unscaled, precision, scale) in [
12360            (9007199254740991i128, 38u8, 6i8), // last integer exact in an f64
12361            (9007199254740992, 38, 6),         // 2^53, the first that is not
12362            (9007199254740993, 38, 6),         // one past that
12363            (16777215, 38, 3),                 // last integer exact in an f32
12364            (16777216, 38, 3),                 // 2^24, the first that is not
12365            (16777217, 38, 3),                 // one past that
12366            (123456789, 38, 10),               // last exact power of ten for an f32
12367            (123456789, 38, 11),               // one past it
12368            (123456789, 38, 22),               // last exact power of ten for an f64
12369            (123456789, 38, 23),               // one past it
12370            (12345, 38, 0),                    // lowest scale the division handles
12371            (12345, 38, -1),                   // one below it: negative scales
12372            (12345, 38, -23),                  //   are all rescaled as text
12373            // only the upper bound of a scale is validated, so this is legal
12374            (i128::MAX, 38, i8::MIN),
12375            (999999999999999, 15, 3), // widest value precision 15 allows
12376            (-999999999999999, 15, 15),
12377            (999999999999999, 16, 3), // one precision past the skipped test
12378            (9999999, 7, 3),          // widest value precision 7 allows
12379            (-9999999, 7, 7),
12380            (9999999, 8, 3), // one precision past it, for `f32`
12381            (-99999999999999999999999999999999999999, 38, 20),
12382            (1, 38, 38),
12383        ] {
12384            let text = Decimal128Type::format_decimal(unscaled, u8::MAX, scale);
12385            let array = decimal128(unscaled, precision, scale);
12386            let label = format!("Decimal128({unscaled}, precision={precision}, scale={scale})");
12387
12388            let as_f64 = cast(&array, &DataType::Float64).unwrap();
12389            assert_eq!(
12390                as_f64.as_primitive::<Float64Type>().value(0),
12391                text.parse::<f64>().unwrap(),
12392                "{label} -> Float64 disagrees with parsing {text:?}"
12393            );
12394
12395            let as_f32 = cast(&array, &DataType::Float32).unwrap();
12396            assert_eq!(
12397                as_f32.as_primitive::<Float32Type>().value(0),
12398                text.parse::<f32>().unwrap(),
12399                "{label} -> Float32 disagrees with parsing {text:?}"
12400            );
12401        }
12402    }
12403
12404    #[test]
12405    fn test_cast_decimal256_to_float_is_correctly_rounded() {
12406        for (unscaled, scale) in [
12407            ("12345678901234567890", 2i8),
12408            ("10000000000000000000000000000000000000", 37),
12409            ("13631072500000000514758830", 18),
12410            ("123456", 3),
12411        ] {
12412            let value = i256::from_string(unscaled).unwrap();
12413            let array = Decimal256Array::from(vec![value])
12414                .with_precision_and_scale(76, scale)
12415                .unwrap();
12416            let text = Decimal256Type::format_decimal(value, u8::MAX, scale);
12417
12418            let as_f64 = cast(&array, &DataType::Float64).unwrap();
12419            assert_eq!(
12420                as_f64.as_primitive::<Float64Type>().value(0),
12421                text.parse::<f64>().unwrap(),
12422                "Decimal256({unscaled}, scale={scale}) -> Float64"
12423            );
12424
12425            let as_f32 = cast(&array, &DataType::Float32).unwrap();
12426            assert_eq!(
12427                as_f32.as_primitive::<Float32Type>().value(0),
12428                text.parse::<f32>().unwrap(),
12429                "Decimal256({unscaled}, scale={scale}) -> Float32"
12430            );
12431        }
12432    }
12433
12434    #[test]
12435    fn test_cast_decimal_to_float_saturates_out_of_range() {
12436        // 1.7e39: past f32::MAX, still far inside f64.
12437        for (unscaled, want_f32) in [(i128::MAX, f32::INFINITY), (i128::MIN, f32::NEG_INFINITY)] {
12438            let array = decimal128(unscaled, 38, -1);
12439
12440            let as_f32 = cast(&array, &DataType::Float32).unwrap();
12441            assert_eq!(as_f32.as_primitive::<Float32Type>().value(0), want_f32);
12442
12443            let text = Decimal128Type::format_decimal(unscaled, u8::MAX, -1);
12444            let as_f64 = cast(&array, &DataType::Float64).unwrap();
12445            assert_eq!(
12446                as_f64.as_primitive::<Float64Type>().value(0),
12447                text.parse::<f64>().unwrap()
12448            );
12449        }
12450
12451        // 1e-76: below the smallest f32 subnormal, representable in an f64.
12452        let array = Decimal256Array::from(vec![i256::from(1)])
12453            .with_precision_and_scale(76, 76)
12454            .unwrap();
12455
12456        let as_f32 = cast(&array, &DataType::Float32).unwrap();
12457        assert_eq!(as_f32.as_primitive::<Float32Type>().value(0), 0.0);
12458
12459        let as_f64 = cast(&array, &DataType::Float64).unwrap();
12460        assert_eq!(as_f64.as_primitive::<Float64Type>().value(0), 1e-76);
12461    }
12462
12463    #[test]
12464    fn test_single_decimal_to_float_lossy_scale_outside_i8() {
12465        // `format_decimal` takes an `i8` scale; narrowing 128 into one wraps it to
12466        // -128 and turns 1e-128 into 1e128. The edges of the `i8` range still round
12467        // once, and anything past them falls back to the division.
12468        let as_float = |x: i128| x as f64;
12469        let lossy =
12470            |scale: i32| single_decimal_to_float_lossy::<Decimal128Type, _>(&as_float, 1, scale);
12471        for scale in [i8::MAX, i8::MIN] {
12472            let text = Decimal128Type::format_decimal(1, u8::MAX, scale);
12473            assert_eq!(
12474                lossy(scale.into()),
12475                text.parse::<f64>().unwrap(),
12476                "scale={scale}"
12477            );
12478        }
12479        for scale in [128, -129] {
12480            assert_eq!(lossy(scale), 1.0 / 10_f64.powi(scale), "scale={scale}");
12481        }
12482    }
12483
12484    // Keeping only `MAX_PRECISION` digits would scale the result by ten.
12485    #[test]
12486    fn test_cast_decimal_to_float_keeps_digits_beyond_declared_precision() {
12487        // 39 digits, one more than `Decimal128Type::MAX_PRECISION`.
12488        let array = decimal128(i128::MAX, 38, 0);
12489
12490        let as_f64 = cast(&array, &DataType::Float64).unwrap();
12491        assert_eq!(
12492            as_f64.as_primitive::<Float64Type>().value(0),
12493            1.7014118346046923e38 // 2^127, the double nearest i128::MAX
12494        );
12495
12496        let as_f32 = cast(&array, &DataType::Float32).unwrap();
12497        assert_eq!(
12498            as_f32.as_primitive::<Float32Type>().value(0),
12499            1.7014118e38 // 2^127, the float nearest i128::MAX
12500        );
12501
12502        // A precision of 15 (7 for `f32`) promises an integer the float holds
12503        // exactly, but values are not validated against the precision they declare.
12504        for (unscaled, precision, scale) in
12505            [(12345678901234567890i128, 15u8, 2i8), (16777217, 7, 1)]
12506        {
12507            let text = Decimal128Type::format_decimal(unscaled, u8::MAX, scale);
12508            let array = decimal128(unscaled, precision, scale);
12509
12510            let as_f64 = cast(&array, &DataType::Float64).unwrap();
12511            assert_eq!(
12512                as_f64.as_primitive::<Float64Type>().value(0),
12513                text.parse::<f64>().unwrap(),
12514                "{text} at precision {precision} -> Float64"
12515            );
12516
12517            let as_f32 = cast(&array, &DataType::Float32).unwrap();
12518            assert_eq!(
12519                as_f32.as_primitive::<Float32Type>().value(0),
12520                text.parse::<f32>().unwrap(),
12521                "{text} at precision {precision} -> Float32"
12522            );
12523        }
12524    }
12525}