#[macro_export]
macro_rules! newtype_datatype {
($newtype:ty, $repr:ty) => {
$crate::newtype_datatype!($newtype, $repr, noref);
impl $crate::RefDatatype for $newtype {
type Ref = <$repr as $crate::RefDatatype>::Ref;
fn value_ref(typed: &Self::Typed, index: usize) -> &Self::Ref {
<$repr as $crate::RefDatatype>::value_ref(typed, index)
}
}
};
($newtype:ty, $repr:ty, primitive) => {
$crate::newtype_datatype!($newtype, $repr);
impl $crate::PrimitiveDatatype for $newtype {
type Native = <$repr as $crate::PrimitiveDatatype>::Native;
fn values(typed: &Self::Typed) -> &[Self::Native] {
<$repr as $crate::PrimitiveDatatype>::values(typed)
}
}
};
($newtype:ty, $repr:ty, noref) => {
impl $crate::Datatype for $newtype {
const NULLABLE: bool = <$repr as $crate::Datatype>::NULLABLE;
type Typed = <$repr as $crate::Datatype>::Typed;
type Value<'a>
= <$repr as $crate::Datatype>::Value<'a>
where
Self: 'a;
type Owned = $newtype;
fn datatype() -> $crate::arrow::datatypes::DataType {
<$repr as $crate::Datatype>::datatype()
}
fn matches(actual: &$crate::arrow::datatypes::DataType) -> bool {
<$repr as $crate::Datatype>::matches(actual)
}
fn downcast(
array: &dyn $crate::arrow::array::Array,
) -> ::core::result::Result<Self::Typed, $crate::ColumnError> {
<$repr as $crate::Datatype>::downcast(array)
}
fn is_null(typed: &Self::Typed, index: usize) -> bool {
<$repr as $crate::Datatype>::is_null(typed, index)
}
fn value(typed: &Self::Typed, index: usize) -> Self::Value<'_> {
<$repr as $crate::Datatype>::value(typed, index)
}
fn build(
values: impl ::core::iter::Iterator<Item = ::core::option::Option<Self::Owned>>,
) -> ::core::result::Result<$crate::arrow::array::ArrayRef, $crate::ColumnError> {
<$repr as $crate::Datatype>::build(
values.map(|value| value.map(::core::convert::Into::into)),
)
}
fn to_owned_value(value: Self::Value<'_>) -> Self::Owned {
::core::convert::From::from(<$repr as $crate::Datatype>::to_owned_value(value))
}
}
impl $crate::InfallibleBuild for $newtype where $repr: $crate::InfallibleBuild {}
};
}
use std::marker::PhantomData;
use crate::datatype::{ColumnError, Datatype, InfallibleBuild, PrimitiveDatatype, RefDatatype};
pub struct As<T, Repr> {
_marker: PhantomData<fn() -> (T, Repr)>,
}
impl<T, Repr> Datatype for As<T, Repr>
where
T: 'static,
Repr: Datatype + 'static,
T: From<Repr::Owned>,
Repr::Owned: From<T>,
{
const NULLABLE: bool = Repr::NULLABLE;
type Typed = Repr::Typed;
type Value<'a>
= Repr::Value<'a>
where
Self: 'a;
type Owned = T;
fn datatype() -> arrow::datatypes::DataType {
Repr::datatype()
}
fn matches(actual: &arrow::datatypes::DataType) -> bool {
Repr::matches(actual)
}
fn downcast(array: &dyn arrow::array::Array) -> Result<Self::Typed, ColumnError> {
Repr::downcast(array)
}
fn is_null(typed: &Self::Typed, index: usize) -> bool {
Repr::is_null(typed, index)
}
fn value(typed: &Self::Typed, index: usize) -> Self::Value<'_> {
Repr::value(typed, index)
}
fn build(
values: impl Iterator<Item = Option<Self::Owned>>,
) -> Result<arrow::array::ArrayRef, ColumnError> {
Repr::build(values.map(|value| value.map(Repr::Owned::from)))
}
fn to_owned_value(value: Self::Value<'_>) -> Self::Owned {
T::from(Repr::to_owned_value(value))
}
}
impl<T, Repr> InfallibleBuild for As<T, Repr>
where
T: 'static,
Repr: Datatype + InfallibleBuild + 'static,
T: From<Repr::Owned>,
Repr::Owned: From<T>,
{
}
impl<T, Repr> RefDatatype for As<T, Repr>
where
T: 'static,
Repr: RefDatatype + 'static,
T: From<Repr::Owned>,
Repr::Owned: From<T>,
{
type Ref = Repr::Ref;
fn value_ref(typed: &Self::Typed, index: usize) -> &Self::Ref {
Repr::value_ref(typed, index)
}
}
impl<T, Repr> PrimitiveDatatype for As<T, Repr>
where
T: 'static,
Repr: PrimitiveDatatype + 'static,
T: From<Repr::Owned>,
Repr::Owned: From<T>,
{
type Native = Repr::Native;
fn values(typed: &Self::Typed) -> &[Self::Native] {
Repr::values(typed)
}
}