arrow_array/array/
null_array.rs1use crate::builder::NullBuilder;
21use crate::{Array, ArrayRef};
22use arrow_buffer::buffer::NullBuffer;
23use arrow_data::{ArrayData, ArrayDataBuilder};
24use arrow_schema::DataType;
25use std::any::Any;
26use std::sync::Arc;
27
28#[derive(Clone)]
46pub struct NullArray {
47 len: usize,
48}
49
50impl NullArray {
51 pub fn new(length: usize) -> Self {
57 Self { len: length }
58 }
59
60 pub fn slice(&self, offset: usize, len: usize) -> Self {
62 assert!(
63 offset.saturating_add(len) <= self.len,
64 "the length + offset of the sliced BooleanBuffer cannot exceed the existing length"
65 );
66
67 Self { len }
68 }
69
70 pub fn builder(_capacity: usize) -> NullBuilder {
75 NullBuilder::new()
76 }
77}
78
79impl Array for NullArray {
80 fn as_any(&self) -> &dyn Any {
81 self
82 }
83
84 fn to_data(&self) -> ArrayData {
85 self.clone().into()
86 }
87
88 fn into_data(self) -> ArrayData {
89 self.into()
90 }
91
92 fn data_type(&self) -> &DataType {
93 &DataType::Null
94 }
95
96 fn slice(&self, offset: usize, length: usize) -> ArrayRef {
97 Arc::new(self.slice(offset, length))
98 }
99
100 fn len(&self) -> usize {
101 self.len
102 }
103
104 fn is_empty(&self) -> bool {
105 self.len == 0
106 }
107
108 fn offset(&self) -> usize {
109 0
110 }
111
112 fn nulls(&self) -> Option<&NullBuffer> {
113 None
114 }
115
116 fn logical_nulls(&self) -> Option<NullBuffer> {
117 (self.len != 0).then(|| NullBuffer::new_null(self.len))
118 }
119
120 fn is_nullable(&self) -> bool {
121 !self.is_empty()
122 }
123
124 fn logical_null_count(&self) -> usize {
125 self.len
126 }
127
128 fn get_buffer_memory_size(&self) -> usize {
129 0
130 }
131
132 fn get_array_memory_size(&self) -> usize {
133 std::mem::size_of::<Self>()
134 }
135}
136
137impl From<ArrayData> for NullArray {
138 fn from(data: ArrayData) -> Self {
139 assert_eq!(
140 data.data_type(),
141 &DataType::Null,
142 "NullArray data type should be Null"
143 );
144 assert_eq!(
145 data.buffers().len(),
146 0,
147 "NullArray data should contain 0 buffers"
148 );
149 assert!(
150 data.nulls().is_none(),
151 "NullArray data should not contain a null buffer, as no buffers are required"
152 );
153 Self { len: data.len() }
154 }
155}
156
157impl From<NullArray> for ArrayData {
158 fn from(array: NullArray) -> Self {
159 let builder = ArrayDataBuilder::new(DataType::Null).len(array.len);
160 unsafe { builder.build_unchecked() }
161 }
162}
163
164impl std::fmt::Debug for NullArray {
165 fn fmt(&self, f: &mut std::fmt::Formatter) -> std::fmt::Result {
166 write!(f, "NullArray({})", self.len())
167 }
168}
169
170#[cfg(test)]
171mod tests {
172 use super::*;
173 use crate::{make_array, Int64Array, StructArray};
174 use arrow_data::transform::MutableArrayData;
175 use arrow_schema::Field;
176
177 #[test]
178 fn test_null_array() {
179 let null_arr = NullArray::new(32);
180
181 assert_eq!(null_arr.len(), 32);
182 assert_eq!(null_arr.null_count(), 0);
183 assert_eq!(null_arr.logical_null_count(), 32);
184 assert_eq!(null_arr.logical_nulls().unwrap().null_count(), 32);
185 assert!(null_arr.is_valid(0));
186 assert!(null_arr.is_nullable());
187 }
188
189 #[test]
190 fn test_null_array_slice() {
191 let array1 = NullArray::new(32);
192
193 let array2 = array1.slice(8, 16);
194 assert_eq!(array2.len(), 16);
195 assert_eq!(array2.null_count(), 0);
196 assert_eq!(array2.logical_null_count(), 16);
197 assert_eq!(array2.logical_nulls().unwrap().null_count(), 16);
198 assert!(array2.is_valid(0));
199 assert!(array2.is_nullable());
200 }
201
202 #[test]
203 fn test_debug_null_array() {
204 let array = NullArray::new(1024 * 1024);
205 assert_eq!(format!("{array:?}"), "NullArray(1048576)");
206 }
207
208 #[test]
209 fn test_null_array_with_parent_null_buffer() {
210 let null_array = NullArray::new(1);
211 let int_array = Int64Array::from(vec![42]);
212
213 let fields = vec![
214 Field::new("a", DataType::Int64, true),
215 Field::new("b", DataType::Null, true),
216 ];
217
218 let struct_array_data = ArrayData::builder(DataType::Struct(fields.into()))
219 .len(1)
220 .add_child_data(int_array.to_data())
221 .add_child_data(null_array.to_data())
222 .build()
223 .unwrap();
224
225 let mut mutable = MutableArrayData::new(vec![&struct_array_data], true, 1);
226
227 mutable.extend_nulls(1);
230 let data = mutable.freeze();
231
232 let struct_array = Arc::new(StructArray::from(data.clone()));
233 assert!(make_array(data) == struct_array);
234 }
235}