Thanks to visit codestin.com
Credit goes to docs.rs

arrow2/array/
null.rs

1use crate::{bitmap::Bitmap, datatypes::DataType};
2use std::any::Any;
3
4use crate::array::MutableArray;
5use crate::bitmap::MutableBitmap;
6use crate::{
7    array::{Array, FromFfi, ToFfi},
8    datatypes::PhysicalType,
9    error::Error,
10    ffi,
11};
12
13/// The concrete [`Array`] of [`DataType::Null`].
14#[derive(Clone)]
15pub struct NullArray {
16    data_type: DataType,
17    length: usize,
18}
19
20impl NullArray {
21    /// Returns a new [`NullArray`].
22    /// # Errors
23    /// This function errors iff:
24    /// * The `data_type`'s [`crate::datatypes::PhysicalType`] is not equal to [`crate::datatypes::PhysicalType::Null`].
25    pub fn try_new(data_type: DataType, length: usize) -> Result<Self, Error> {
26        if data_type.to_physical_type() != PhysicalType::Null {
27            return Err(Error::oos(
28                "NullArray can only be initialized with a DataType whose physical type is Boolean",
29            ));
30        }
31
32        Ok(Self { data_type, length })
33    }
34
35    /// Returns a new [`NullArray`].
36    /// # Panics
37    /// This function errors iff:
38    /// * The `data_type`'s [`crate::datatypes::PhysicalType`] is not equal to [`crate::datatypes::PhysicalType::Null`].
39    pub fn new(data_type: DataType, length: usize) -> Self {
40        Self::try_new(data_type, length).unwrap()
41    }
42
43    /// Returns a new empty [`NullArray`].
44    pub fn new_empty(data_type: DataType) -> Self {
45        Self::new(data_type, 0)
46    }
47
48    /// Returns a new [`NullArray`].
49    pub fn new_null(data_type: DataType, length: usize) -> Self {
50        Self::new(data_type, length)
51    }
52
53    impl_sliced!();
54    impl_into_array!();
55}
56
57impl NullArray {
58    /// Returns a slice of the [`NullArray`].
59    /// # Panic
60    /// This function panics iff `offset + length > self.len()`.
61    pub fn slice(&mut self, offset: usize, length: usize) {
62        assert!(
63            offset + length <= self.len(),
64            "the offset of the new array cannot exceed the arrays' length"
65        );
66        unsafe { self.slice_unchecked(offset, length) };
67    }
68
69    /// Returns a slice of the [`NullArray`].
70    /// # Safety
71    /// The caller must ensure that `offset + length < self.len()`.
72    pub unsafe fn slice_unchecked(&mut self, _offset: usize, length: usize) {
73        self.length = length;
74    }
75
76    #[inline]
77    fn len(&self) -> usize {
78        self.length
79    }
80}
81
82impl Array for NullArray {
83    impl_common_array!();
84
85    fn validity(&self) -> Option<&Bitmap> {
86        None
87    }
88
89    fn with_validity(&self, _: Option<Bitmap>) -> Box<dyn Array> {
90        panic!("cannot set validity of a null array")
91    }
92}
93
94#[derive(Debug)]
95/// A distinct type to disambiguate
96/// clashing methods
97pub struct MutableNullArray {
98    inner: NullArray,
99}
100
101impl MutableNullArray {
102    /// Returns a new [`MutableNullArray`].
103    /// # Panics
104    /// This function errors iff:
105    /// * The `data_type`'s [`crate::datatypes::PhysicalType`] is not equal to [`crate::datatypes::PhysicalType::Null`].
106    pub fn new(data_type: DataType, length: usize) -> Self {
107        let inner = NullArray::try_new(data_type, length).unwrap();
108        Self { inner }
109    }
110}
111
112impl From<MutableNullArray> for NullArray {
113    fn from(value: MutableNullArray) -> Self {
114        value.inner
115    }
116}
117
118impl MutableArray for MutableNullArray {
119    fn data_type(&self) -> &DataType {
120        &DataType::Null
121    }
122
123    fn len(&self) -> usize {
124        self.inner.length
125    }
126
127    fn validity(&self) -> Option<&MutableBitmap> {
128        None
129    }
130
131    fn as_box(&mut self) -> Box<dyn Array> {
132        self.inner.clone().boxed()
133    }
134
135    fn as_any(&self) -> &dyn Any {
136        self
137    }
138
139    fn as_mut_any(&mut self) -> &mut dyn Any {
140        self
141    }
142
143    fn push_null(&mut self) {
144        self.inner.length += 1;
145    }
146
147    fn reserve(&mut self, _additional: usize) {
148        // no-op
149    }
150
151    fn shrink_to_fit(&mut self) {
152        // no-op
153    }
154}
155
156impl std::fmt::Debug for NullArray {
157    fn fmt(&self, f: &mut std::fmt::Formatter<'_>) -> std::fmt::Result {
158        write!(f, "NullArray({})", self.len())
159    }
160}
161
162unsafe impl ToFfi for NullArray {
163    fn buffers(&self) -> Vec<Option<*const u8>> {
164        // `None` is technically not required by the specification, but older C++ implementations require it, so leaving
165        // it here for backward compatibility
166        vec![None]
167    }
168
169    fn offset(&self) -> Option<usize> {
170        Some(0)
171    }
172
173    fn to_ffi_aligned(&self) -> Self {
174        self.clone()
175    }
176}
177
178impl<A: ffi::ArrowArrayRef> FromFfi<A> for NullArray {
179    unsafe fn try_from_ffi(array: A) -> Result<Self, Error> {
180        let data_type = array.data_type().clone();
181        Self::try_new(data_type, array.array().len())
182    }
183}
184
185#[cfg(feature = "arrow")]
186mod arrow {
187    use super::*;
188    use arrow_data::{ArrayData, ArrayDataBuilder};
189    impl NullArray {
190        /// Convert this array into [`arrow_data::ArrayData`]
191        pub fn to_data(&self) -> ArrayData {
192            let builder = ArrayDataBuilder::new(arrow_schema::DataType::Null).len(self.len());
193
194            // Safety: safe by construction
195            unsafe { builder.build_unchecked() }
196        }
197
198        /// Create this array from [`ArrayData`]
199        pub fn from_data(data: &ArrayData) -> Self {
200            Self::new(DataType::Null, data.len())
201        }
202    }
203}