use std::borrow::Borrow;
use crate::{
array::{
MutableArray, MutableBinaryArray, MutableBinaryValuesArray, MutableBooleanArray,
MutableFixedSizeBinaryArray, MutablePrimitiveArray, MutableUtf8Array,
MutableUtf8ValuesArray,
},
offset::Offset,
types::NativeType,
};
pub trait Indexable {
type Value<'a>: Borrow<Self::Type>
where
Self: 'a;
type Type: ?Sized;
fn value_at(&self, index: usize) -> Self::Value<'_>;
#[inline]
unsafe fn value_unchecked_at(&self, index: usize) -> Self::Value<'_> {
self.value_at(index)
}
}
pub trait AsIndexed<M: Indexable> {
fn as_indexed(&self) -> &M::Type;
}
impl Indexable for MutableBooleanArray {
type Value<'a> = bool;
type Type = bool;
#[inline]
fn value_at(&self, i: usize) -> Self::Value<'_> {
self.values().get(i)
}
}
impl AsIndexed<MutableBooleanArray> for bool {
#[inline]
fn as_indexed(&self) -> &bool {
self
}
}
impl<O: Offset> Indexable for MutableBinaryArray<O> {
type Value<'a> = &'a [u8];
type Type = [u8];
#[inline]
fn value_at(&self, i: usize) -> Self::Value<'_> {
assert!(i < self.len());
unsafe { self.value_unchecked_at(i) }
}
#[inline]
unsafe fn value_unchecked_at(&self, i: usize) -> Self::Value<'_> {
let (start, end) = self.offsets().start_end_unchecked(i);
self.values().get_unchecked(start..end)
}
}
impl<O: Offset> AsIndexed<MutableBinaryArray<O>> for &[u8] {
#[inline]
fn as_indexed(&self) -> &[u8] {
self
}
}
impl<O: Offset> Indexable for MutableBinaryValuesArray<O> {
type Value<'a> = &'a [u8];
type Type = [u8];
#[inline]
fn value_at(&self, i: usize) -> Self::Value<'_> {
self.value(i)
}
#[inline]
unsafe fn value_unchecked_at(&self, i: usize) -> Self::Value<'_> {
self.value_unchecked(i)
}
}
impl<O: Offset> AsIndexed<MutableBinaryValuesArray<O>> for &[u8] {
#[inline]
fn as_indexed(&self) -> &[u8] {
self
}
}
impl Indexable for MutableFixedSizeBinaryArray {
type Value<'a> = &'a [u8];
type Type = [u8];
#[inline]
fn value_at(&self, i: usize) -> Self::Value<'_> {
self.value(i)
}
#[inline]
unsafe fn value_unchecked_at(&self, i: usize) -> Self::Value<'_> {
self.value_unchecked(i)
}
}
impl AsIndexed<MutableFixedSizeBinaryArray> for &[u8] {
#[inline]
fn as_indexed(&self) -> &[u8] {
self
}
}
impl<T: NativeType> Indexable for MutablePrimitiveArray<T> {
type Value<'a> = T;
type Type = T;
#[inline]
fn value_at(&self, i: usize) -> Self::Value<'_> {
assert!(i < self.len());
unsafe { self.value_unchecked_at(i) }
}
#[inline]
unsafe fn value_unchecked_at(&self, i: usize) -> Self::Value<'_> {
*self.values().get_unchecked(i)
}
}
impl<T: NativeType> AsIndexed<MutablePrimitiveArray<T>> for T {
#[inline]
fn as_indexed(&self) -> &T {
self
}
}
impl<O: Offset> Indexable for MutableUtf8Array<O> {
type Value<'a> = &'a str;
type Type = str;
#[inline]
fn value_at(&self, i: usize) -> Self::Value<'_> {
self.value(i)
}
#[inline]
unsafe fn value_unchecked_at(&self, i: usize) -> Self::Value<'_> {
self.value_unchecked(i)
}
}
impl<O: Offset, V: AsRef<str>> AsIndexed<MutableUtf8Array<O>> for V {
#[inline]
fn as_indexed(&self) -> &str {
self.as_ref()
}
}
impl<O: Offset> Indexable for MutableUtf8ValuesArray<O> {
type Value<'a> = &'a str;
type Type = str;
#[inline]
fn value_at(&self, i: usize) -> Self::Value<'_> {
self.value(i)
}
#[inline]
unsafe fn value_unchecked_at(&self, i: usize) -> Self::Value<'_> {
self.value_unchecked(i)
}
}
impl<O: Offset, V: AsRef<str>> AsIndexed<MutableUtf8ValuesArray<O>> for V {
#[inline]
fn as_indexed(&self) -> &str {
self.as_ref()
}
}