1use crate::cast::*;
6
7pub(crate) fn cast_map_values(
9 from: &MapArray,
10 to_data_type: &DataType,
11 cast_options: &CastOptions,
12 to_ordered: bool,
13) -> Result<ArrayRef, ArrowError> {
14 let DataType::Map(entries_field, _) = to_data_type else {
15 unreachable!("cast_with_options only calls cast_map_values for Map target types");
16 };
17
18 let key_field = key_field(entries_field).ok_or(ArrowError::CastError(
19 "map is missing key field".to_string(),
20 ))?;
21 let value_field = value_field(entries_field).ok_or(ArrowError::CastError(
22 "map is missing value field".to_string(),
23 ))?;
24
25 let offsets = from.offsets();
26 let first = offsets.first();
27 let entries = from
29 .entries()
30 .slice(first.as_usize(), (offsets.last() - first).as_usize());
31 let key_array = cast_with_options(entries.column(0), key_field.data_type(), cast_options)?;
32 let value_array = cast_with_options(entries.column(1), value_field.data_type(), cast_options)?;
33
34 Ok(Arc::new(MapArray::try_new(
35 entries_field.clone(),
36 offsets.clone().subtract(first),
37 StructArray::try_new(
38 Fields::from(vec![key_field, value_field]),
39 vec![key_array, value_array],
40 entries.nulls().cloned(),
41 )?,
42 from.nulls().cloned(),
43 to_ordered,
44 )?))
45}
46
47pub(crate) fn key_field(entries_field: &FieldRef) -> Option<FieldRef> {
49 if let DataType::Struct(fields) = entries_field.data_type() {
50 fields.first().cloned()
51 } else {
52 None
53 }
54}
55
56pub(crate) fn value_field(entries_field: &FieldRef) -> Option<FieldRef> {
58 if let DataType::Struct(fields) = entries_field.data_type() {
59 fields.get(1).cloned()
60 } else {
61 None
62 }
63}