Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 0 additions & 2 deletions vortex-array/public-api.lock
Original file line number Diff line number Diff line change
Expand Up @@ -13576,8 +13576,6 @@ pub struct vortex_array::patches::Patches

impl vortex_array::patches::Patches

pub unsafe fn vortex_array::patches::Patches::apply_to_buffer<P: vortex_array::dtype::NativePType>(&self, buffer: &mut [P], validity: &mut vortex_mask::mask_mut::MaskMut, ctx: &mut vortex_array::ExecutionCtx)

pub fn vortex_array::patches::Patches::array_len(&self) -> usize

pub fn vortex_array::patches::Patches::cast_values(self, values_dtype: &vortex_array::dtype::DType) -> vortex_error::VortexResult<Self>
Expand Down
134 changes: 0 additions & 134 deletions vortex-array/src/patches.rs
Original file line number Diff line number Diff line change
Expand Up @@ -6,28 +6,23 @@ use std::fmt::Debug;
use std::hash::Hash;
use std::ops::Range;

use itertools::Itertools;
use num_traits::NumCast;
use vortex_buffer::BitBuffer;
use vortex_buffer::BufferMut;
use vortex_error::VortexError;
use vortex_error::VortexExpect;
use vortex_error::VortexResult;
use vortex_error::vortex_bail;
use vortex_error::vortex_ensure;
use vortex_error::vortex_err;
use vortex_mask::AllOr;
use vortex_mask::Mask;
use vortex_mask::MaskMut;
use vortex_utils::aliases::hash_map::HashMap;

use crate::ArrayRef;
use crate::ExecutionCtx;
use crate::IntoArray;
use crate::ToCanonical;
use crate::arrays::BoolArray;
use crate::arrays::PrimitiveArray;
use crate::arrays::bool::BoolArrayExt;
use crate::builtins::ArrayBuiltins;
use crate::dtype::DType;
use crate::dtype::IntegerPType;
Expand Down Expand Up @@ -868,59 +863,6 @@ impl Patches {
}))
}

/// Apply patches to a mutable buffer and validity mask.
///
/// This method applies the patch values to the given buffer at the positions specified by the
/// patch indices. For non-null patch values, it updates the buffer and marks the position as
/// valid. For null patch values, it marks the position as invalid.
///
/// # Safety
///
/// - All patch indices after offset adjustment must be valid indices into the buffer.
/// - The buffer and validity mask must have the same length.
pub unsafe fn apply_to_buffer<P: NativePType>(
&self,
buffer: &mut [P],
validity: &mut MaskMut,
ctx: &mut ExecutionCtx,
) {
let patch_indices = self
.indices
.clone()
.execute::<PrimitiveArray>(ctx)
.vortex_expect("patch indices must be convertible to PrimitiveArray");
let patch_values = self
.values
.clone()
.execute::<PrimitiveArray>(ctx)
.vortex_expect("patch values must be convertible to PrimitiveArray");
let patches_validity = patch_values
.validity()
.vortex_expect("patch values validity should be derivable");

let patch_values_slice = patch_values.as_slice::<P>();
match_each_unsigned_integer_ptype!(patch_indices.ptype(), |I| {
let patch_indices_slice = patch_indices.as_slice::<I>();

// SAFETY:
// - `Patches` invariant guarantees indices are sorted and within array bounds.
// - `patch_indices` and `patch_values` have equal length (from `Patches` invariant).
// - `buffer` and `validity` have equal length (precondition).
// - All patch indices are valid after offset adjustment (precondition).
unsafe {
apply_patches_to_buffer_inner(
buffer,
validity,
patch_indices_slice,
self.offset,
patch_values_slice,
&patches_validity,
ctx,
);
}
});
}

pub fn map_values<F>(self, f: F) -> VortexResult<Self>
where
F: FnOnce(ArrayRef) -> VortexResult<ArrayRef>,
Expand All @@ -945,82 +887,6 @@ impl Patches {
}
}

/// Helper function to apply patches to a buffer.
///
/// # Safety
///
/// - All indices in `patch_indices` after subtracting `patch_offset` must be valid indices
/// into both `buffer` and `validity`.
/// - `patch_indices` must be sorted in ascending order.
/// - `patch_indices` and `patch_values` must have the same length.
/// - `buffer` and `validity` must have the same length.
unsafe fn apply_patches_to_buffer_inner<P, I>(
buffer: &mut [P],
validity: &mut MaskMut,
patch_indices: &[I],
patch_offset: usize,
patch_values: &[P],
patches_validity: &Validity,
ctx: &mut ExecutionCtx,
) where
P: NativePType,
I: UnsignedPType,
{
debug_assert!(!patch_indices.is_empty());
debug_assert_eq!(patch_indices.len(), patch_values.len());
debug_assert_eq!(buffer.len(), validity.len());

match patches_validity {
Validity::NonNullable | Validity::AllValid => {
// All patch values are valid, apply them all.
for (&i, &value) in patch_indices.iter().zip_eq(patch_values) {
let index = i.as_() - patch_offset;

// SAFETY: `index` is valid because caller guarantees all patch indices are within
// bounds after offset adjustment.
unsafe {
validity.set_unchecked(index);
}
buffer[index] = value;
}
}
Validity::AllInvalid => {
// All patch values are null, just mark positions as invalid.
for &i in patch_indices {
let index = i.as_() - patch_offset;

// SAFETY: `index` is valid because caller guarantees all patch indices are within
// bounds after offset adjustment.
unsafe {
validity.unset_unchecked(index);
}
}
}
Validity::Array(array) => {
// Some patch values may be null, check each one.
let bool_array = array
.clone()
.execute::<BoolArray>(ctx)
.vortex_expect("validity array must be convertible to BoolArray");
let mask = bool_array.to_bit_buffer();
for (patch_idx, (&i, &value)) in patch_indices.iter().zip_eq(patch_values).enumerate() {
let index = i.as_() - patch_offset;

// SAFETY: `index` and `patch_idx` are valid because caller guarantees all patch
// indices are within bounds after offset adjustment.
unsafe {
if mask.value_unchecked(patch_idx) {
buffer[index] = value;
validity.set_unchecked(index);
} else {
validity.unset_unchecked(index);
}
}
}
}
}
}

#[allow(clippy::too_many_arguments)] // private function, can clean up one day
fn take_map<I: NativePType + Hash + Eq + TryFrom<usize>, T: NativePType>(
indices: &[I],
Expand Down
18 changes: 1 addition & 17 deletions vortex-buffer/public-api.lock
Original file line number Diff line number Diff line change
Expand Up @@ -430,16 +430,12 @@ pub fn vortex_buffer::BitBufferMut::append_n(&mut self, value: bool, n: usize)

pub fn vortex_buffer::BitBufferMut::append_true(&mut self)

pub fn vortex_buffer::BitBufferMut::as_mut_ptr(&mut self) -> *mut u8

pub fn vortex_buffer::BitBufferMut::as_mut_slice(&mut self) -> &mut [u8]

pub fn vortex_buffer::BitBufferMut::as_slice(&self) -> &[u8]

pub fn vortex_buffer::BitBufferMut::capacity(&self) -> usize

pub fn vortex_buffer::BitBufferMut::chunks(&self) -> arrow_buffer::util::bit_chunk_iterator::BitChunks<'_>

pub fn vortex_buffer::BitBufferMut::clear(&mut self)

pub fn vortex_buffer::BitBufferMut::collect_bool<F: core::ops::function::FnMut(usize) -> bool>(len: usize, f: F) -> Self
Expand All @@ -448,8 +444,6 @@ pub fn vortex_buffer::BitBufferMut::copy_from(bit_buffer: &vortex_buffer::BitBuf

pub fn vortex_buffer::BitBufferMut::empty() -> Self

pub fn vortex_buffer::BitBufferMut::false_count(&self) -> usize

pub fn vortex_buffer::BitBufferMut::fill_range(&mut self, start: usize, end: usize, value: bool)

pub unsafe fn vortex_buffer::BitBufferMut::fill_range_unchecked(&mut self, start: usize, end: usize, value: bool)
Expand Down Expand Up @@ -486,14 +480,10 @@ pub fn vortex_buffer::BitBufferMut::set_to(&mut self, index: usize, value: bool)

pub unsafe fn vortex_buffer::BitBufferMut::set_to_unchecked(&mut self, index: usize, value: bool)

pub fn vortex_buffer::BitBufferMut::split_off(&mut self, at: usize) -> Self

pub fn vortex_buffer::BitBufferMut::true_count(&self) -> usize
pub unsafe fn vortex_buffer::BitBufferMut::set_unchecked(&mut self, index: usize)

pub fn vortex_buffer::BitBufferMut::truncate(&mut self, len: usize)

pub fn vortex_buffer::BitBufferMut::unaligned_chunks(&self) -> arrow_buffer::util::bit_chunk_iterator::UnalignedBitChunk<'_>

pub fn vortex_buffer::BitBufferMut::unset(&mut self, index: usize)

pub unsafe fn vortex_buffer::BitBufferMut::unset_unchecked(&mut self, index: usize)
Expand All @@ -510,12 +500,6 @@ impl core::clone::Clone for vortex_buffer::BitBufferMut

pub fn vortex_buffer::BitBufferMut::clone(&self) -> vortex_buffer::BitBufferMut

impl core::cmp::Eq for vortex_buffer::BitBufferMut

impl core::cmp::PartialEq for vortex_buffer::BitBufferMut

pub fn vortex_buffer::BitBufferMut::eq(&self, other: &Self) -> bool

impl core::convert::From<&[bool]> for vortex_buffer::BitBufferMut

pub fn vortex_buffer::BitBufferMut::from(value: &[bool]) -> Self
Expand Down
Loading
Loading