Skip to content

Commit

Permalink
impl Display for StructValue
Browse files Browse the repository at this point in the history
- Further on #670.
- Fixes a bug in `sturct_.rs` wherein the failure condition was reversed.
- Permit `as_list` to convert a `Null` into a `None`.

Examples:

    {}

    {foo:3}

    {foo:3,bar:true}
  • Loading branch information
danking committed Aug 22, 2024
1 parent 4038a40 commit 8b7ca74
Show file tree
Hide file tree
Showing 3 changed files with 115 additions and 4 deletions.
112 changes: 109 additions & 3 deletions vortex-scalar/src/display.rs
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@ use vortex_dtype::{match_each_native_ptype, DType};
use crate::binary::BinaryScalar;
use crate::bool::BoolScalar;
use crate::primitive::PrimitiveScalar;
use crate::struct_::StructScalar;
use crate::utf8::Utf8Scalar;
use crate::Scalar;

Expand Down Expand Up @@ -50,7 +51,26 @@ impl Display for Scalar {
}
}
}
DType::Struct(..) => todo!(),
DType::Struct(dtype, _) => {
let v = StructScalar::try_from(self).map_err(|_| std::fmt::Error)?;

if v.is_null() {
write!(f, "null")
} else {
write!(f, "{{")?;
let formatted_fields = dtype
.names()
.iter()
.enumerate()
.map(|(idx, name)| match v.field_by_idx(idx) {
None => format!("{name}:null"),
Some(val) => format!("{name}:{val}"),
})
.format(",");
write!(f, "{}", formatted_fields)?;
write!(f, "}}")
}
}
DType::List(..) => todo!(),
DType::Extension(..) => todo!(),
}
Expand All @@ -59,11 +79,13 @@ impl Display for Scalar {

#[cfg(test)]
mod tests {
use std::sync::Arc;

use vortex_buffer::Buffer;
use vortex_dtype::Nullability::{NonNullable, Nullable};
use vortex_dtype::{DType, PType};
use vortex_dtype::{DType, PType, StructDType};

use crate::Scalar;
use crate::{PValue, Scalar, ScalarValue};

#[test]
fn display_bool() {
Expand Down Expand Up @@ -109,4 +131,88 @@ mod tests {
);
assert_eq!(format!("{}", Scalar::null(DType::Binary(Nullable))), "null");
}

#[test]
fn display_empty_struct() {
fn dtype() -> DType {
DType::Struct(StructDType::new(Arc::new([]), vec![]), Nullable)
}

assert_eq!(format!("{}", Scalar::null(dtype())), "null");

assert_eq!(format!("{}", Scalar::r#struct(dtype(), vec![])), "{}");
}

#[test]
fn display_one_field_struct() {
fn dtype() -> DType {
DType::Struct(
StructDType::new(
Arc::new([Arc::from("foo")]),
vec![DType::Primitive(PType::U32, Nullable)],
),
Nullable,
)
}

assert_eq!(format!("{}", Scalar::null(dtype())), "null");

assert_eq!(
format!("{}", Scalar::r#struct(dtype(), vec![ScalarValue::Null])),
"{foo:null}"
);

assert_eq!(
format!(
"{}",
Scalar::r#struct(dtype(), vec![ScalarValue::Primitive(PValue::U32(32))])
),
"{foo:32}"
);
}

#[test]
fn display_two_field_struct() {
fn dtype() -> DType {
DType::Struct(
StructDType::new(
Arc::new([Arc::from("foo"), Arc::from("bar")]),
vec![
DType::Bool(Nullable),
DType::Primitive(PType::U32, Nullable),
],
),
Nullable,
)
}

assert_eq!(format!("{}", Scalar::null(dtype())), "null");

assert_eq!(
format!("{}", Scalar::r#struct(dtype(), vec![])),
"{foo:null,bar:null}"
);

assert_eq!(
format!(
"{}",
Scalar::r#struct(dtype(), vec![ScalarValue::Bool(true)])
),
"{foo:true,bar:null}"
);

assert_eq!(
format!(
"{}",
Scalar::r#struct(
dtype(),
vec![
ScalarValue::Bool(true),
ScalarValue::Primitive(PValue::U32(32))
]
)
),
"{foo:true,bar:32}"
);
}
}
6 changes: 5 additions & 1 deletion vortex-scalar/src/struct_.rs
Original file line number Diff line number Diff line change
Expand Up @@ -17,6 +17,10 @@ impl<'a> StructScalar<'a> {
self.dtype
}

pub fn is_null(&self) -> bool {
self.fields.is_none()
}

pub fn field_by_idx(&self, idx: usize) -> Option<Scalar> {
let DType::Struct(st, _) = self.dtype() else {
unreachable!()
Expand Down Expand Up @@ -56,7 +60,7 @@ impl<'a> TryFrom<&'a Scalar> for StructScalar<'a> {
type Error = VortexError;

fn try_from(value: &'a Scalar) -> Result<Self, Self::Error> {
if matches!(value.dtype(), DType::Struct(..)) {
if !matches!(value.dtype(), DType::Struct(..)) {
vortex_bail!("Expected struct scalar, found {}", value.dtype())
}
Ok(Self {
Expand Down
1 change: 1 addition & 0 deletions vortex-scalar/src/value.rs
Original file line number Diff line number Diff line change
Expand Up @@ -61,6 +61,7 @@ impl ScalarValue {

pub fn as_list(&self) -> VortexResult<Option<&Arc<[Self]>>> {
match self {
Self::Null => Ok(None),
Self::List(l) => Ok(Some(l)),
_ => Err(vortex_err!("Expected a list scalar, found {:?}", self)),
}
Expand Down

0 comments on commit 8b7ca74

Please sign in to comment.