use std::hash::Hash;
use vortex_dtype::DType;
use vortex_error::VortexResult;
use vortex_error::vortex_ensure;
use vortex_session::VortexSession;
use crate::ArrayBufferVisitor;
use crate::ArrayChildVisitor;
use crate::ArrayRef;
use crate::EmptyMetadata;
use crate::ExecutionCtx;
use crate::Precision;
use crate::arrays::null::compute::rules::PARENT_RULES;
use crate::buffer::BufferHandle;
use crate::scalar::Scalar;
use crate::serde::ArrayChildren;
use crate::stats::ArrayStats;
use crate::stats::StatsSetRef;
use crate::validity::Validity;
use crate::vtable;
use crate::vtable::ArrayId;
use crate::vtable::BaseArrayVTable;
use crate::vtable::OperationsVTable;
use crate::vtable::VTable;
use crate::vtable::ValidityVTable;
use crate::vtable::VisitorVTable;
pub(crate) mod compute;
vtable!(Null);
impl VTable for NullVTable {
type Array = NullArray;
type Metadata = EmptyMetadata;
type ArrayVTable = Self;
type OperationsVTable = Self;
type ValidityVTable = Self;
type VisitorVTable = Self;
fn id(_array: &Self::Array) -> ArrayId {
Self::ID
}
fn metadata(_array: &NullArray) -> VortexResult<Self::Metadata> {
Ok(EmptyMetadata)
}
fn serialize(_metadata: Self::Metadata) -> VortexResult<Option<Vec<u8>>> {
Ok(Some(vec![]))
}
fn deserialize(
_bytes: &[u8],
_dtype: &DType,
_len: usize,
_buffers: &[BufferHandle],
_session: &VortexSession,
) -> VortexResult<Self::Metadata> {
Ok(EmptyMetadata)
}
fn build(
_dtype: &DType,
len: usize,
_metadata: &Self::Metadata,
_buffers: &[BufferHandle],
_children: &dyn ArrayChildren,
) -> VortexResult<NullArray> {
Ok(NullArray::new(len))
}
fn with_children(_array: &mut Self::Array, children: Vec<ArrayRef>) -> VortexResult<()> {
vortex_ensure!(
children.is_empty(),
"NullArray has no children, got {}",
children.len()
);
Ok(())
}
fn reduce_parent(
array: &Self::Array,
parent: &ArrayRef,
child_idx: usize,
) -> VortexResult<Option<ArrayRef>> {
PARENT_RULES.evaluate(array, parent, child_idx)
}
fn execute(array: &Self::Array, _ctx: &mut ExecutionCtx) -> VortexResult<ArrayRef> {
Ok(array.to_array())
}
}
#[derive(Clone, Debug)]
pub struct NullArray {
len: usize,
stats_set: ArrayStats,
}
#[derive(Debug)]
pub struct NullVTable;
impl NullVTable {
pub const ID: ArrayId = ArrayId::new_ref("vortex.null");
}
impl NullArray {
pub fn new(len: usize) -> Self {
Self {
len,
stats_set: Default::default(),
}
}
}
impl BaseArrayVTable<NullVTable> for NullVTable {
fn len(array: &NullArray) -> usize {
array.len
}
fn dtype(_array: &NullArray) -> &DType {
&DType::Null
}
fn stats(array: &NullArray) -> StatsSetRef<'_> {
array.stats_set.to_ref(array.as_ref())
}
fn array_hash<H: std::hash::Hasher>(array: &NullArray, state: &mut H, _precision: Precision) {
array.len.hash(state);
}
fn array_eq(array: &NullArray, other: &NullArray, _precision: Precision) -> bool {
array.len == other.len
}
}
impl VisitorVTable<NullVTable> for NullVTable {
fn visit_buffers(_array: &NullArray, _visitor: &mut dyn ArrayBufferVisitor) {}
fn visit_children(_array: &NullArray, _visitor: &mut dyn ArrayChildVisitor) {}
fn nchildren(_array: &NullArray) -> usize {
0
}
fn nth_child(_array: &NullArray, _idx: usize) -> Option<ArrayRef> {
None
}
}
impl OperationsVTable<NullVTable> for NullVTable {
fn scalar_at(_array: &NullArray, _index: usize) -> VortexResult<Scalar> {
Ok(Scalar::null(DType::Null))
}
}
impl ValidityVTable<NullVTable> for NullVTable {
fn validity(_array: &NullArray) -> VortexResult<Validity> {
Ok(Validity::AllInvalid)
}
}