Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

CustomType's are Simple not necessarily Classic, and report their TypeTag #328

Merged
merged 1 commit into from
Aug 2, 2023
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
17 changes: 11 additions & 6 deletions src/extensions/rotation.rs
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,7 @@ use pyo3::prelude::*;
use crate::ops::constant::CustomConst;
use crate::resource::{OpDef, ResourceSet, TypeDef};
use crate::types::type_param::TypeArg;
use crate::types::{CustomType, SimpleRow, SimpleType};
use crate::types::{CustomType, SimpleRow, TypeTag};
use crate::Resource;

pub const fn resource_id() -> SmolStr {
Expand All @@ -34,7 +34,7 @@ pub fn resource() -> Resource {
vec![],
HashMap::default(),
|_arg_values: &[TypeArg]| {
let t: SimpleRow = vec![SimpleType::Classic(Type::Angle.custom_type().into())].into();
let t: SimpleRow = vec![Type::Angle.custom_type().into()].into();
Ok((t.clone(), t, ResourceSet::default()))
},
);
Expand Down Expand Up @@ -66,7 +66,7 @@ impl Type {
}

pub fn custom_type(self) -> CustomType {
CustomType::new(self.name(), [], resource_id())
CustomType::new(self.name(), [], resource_id(), TypeTag::Classic)
}

pub fn type_def(self) -> TypeDef {
Expand All @@ -75,7 +75,7 @@ impl Type {
params: vec![],
description: self.description().to_string(),
resource: None,
tag: crate::types::TypeTag::Classic.into(),
tag: TypeTag::Classic.into(),
}
}
}
Expand Down Expand Up @@ -292,7 +292,7 @@ impl Neg for &AngleValue {
#[cfg(test)]
mod test {

use crate::resource::SignatureError;
use crate::{resource::SignatureError, types::TypeTag};

use super::*;

Expand All @@ -306,7 +306,12 @@ mod test {

angle.check_custom(&custom).unwrap();

let false_custom = CustomType::new(custom.name().clone(), vec![], "wrong_resource");
let false_custom = CustomType::new(
custom.name().clone(),
vec![],
"wrong_resource",
TypeTag::Classic,
);
assert_eq!(
angle.check_custom(&false_custom),
Err(SignatureError::ResourceMismatch(
Expand Down
5 changes: 1 addition & 4 deletions src/ops/constant/typecheck.rs
Original file line number Diff line number Diff line change
Expand Up @@ -142,10 +142,7 @@ pub(super) fn typecheck_const(typ: &ClassicType, val: &ConstValue) -> Result<(),
(Container::Sum(_), _) => Err(ConstTypeError::ValueCheckFail(ty.clone(), tm.clone())),
(Container::Opaque(ty), ConstValue::Opaque((ty_act, _val))) => {
if ty_act != ty {
return Err(ConstTypeError::TypeMismatch(
ty.clone().into(),
ty_act.clone().into(),
));
return Err(ConstTypeError::ValueCheckFail(typ.clone(), val.clone()));
}
Ok(())
}
Expand Down
2 changes: 2 additions & 0 deletions src/resource.rs
Original file line number Diff line number Diff line change
Expand Up @@ -494,10 +494,12 @@ impl TypeDef {
) -> Result<CustomType, SignatureError> {
let args = args.into();
self.check_args_impl(&args)?;
let tag = self.tag(&args);
Ok(CustomType::new(
self.name().clone(),
args,
self.resource().expect("Resource not set.").clone(),
tag,
))
}
}
Expand Down
22 changes: 13 additions & 9 deletions src/types/custom.rs
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@ use std::fmt::{self, Display};

use crate::resource::ResourceId;

use super::{type_param::TypeArg, ClassicType, Container};
use super::{type_param::TypeArg, ClassicType, Container, HashableType, SimpleType, TypeTag};

/// An opaque type element. Contains the unique identifier of its definition.
#[derive(Debug, PartialEq, Eq, Clone, serde::Serialize, serde::Deserialize)]
Expand All @@ -21,6 +21,8 @@ pub struct CustomType {
///
/// [`TypeParam`]: super::type_param::TypeParam
args: Vec<TypeArg>,
/// The [TypeTag] describing what can be done to instances of this type
tag: TypeTag,
}

impl CustomType {
Expand All @@ -29,18 +31,15 @@ impl CustomType {
id: impl Into<SmolStr>,
args: impl Into<Vec<TypeArg>>,
resource: impl Into<ResourceId>,
tag: TypeTag,
) -> Self {
Self {
id: id.into(),
args: args.into(),
resource: resource.into(),
tag,
}
}

/// Returns a [`ClassicType`] containing this opaque type.
pub const fn classic_type(self) -> ClassicType {
ClassicType::Container(Container::Opaque(self))
}
}

impl CustomType {
Expand All @@ -66,8 +65,13 @@ impl Display for CustomType {
}
}

impl From<CustomType> for ClassicType {
fn from(ty: CustomType) -> Self {
ty.classic_type()
/// This parallels [SimpleType::new_tuple] and [SimpleType::new_sum]
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I don't see any point in having an equivalent to ClassicType::new_tuple. We can statically rule out ClassicType::new_tuple(...Qubit...) whereas here we cannot, so at best we can only impl TryFrom<CustomType> for ClassicType and you might as well turn the ÇustomType into a SimpleType and try_from that.

impl From<CustomType> for SimpleType {
fn from(value: CustomType) -> Self {
match value.tag {
TypeTag::Simple => SimpleType::Qontainer(Container::Opaque(value)),
TypeTag::Classic => ClassicType::Container(Container::Opaque(value)).into(),
TypeTag::Hashable => HashableType::Container(Container::Opaque(value)).into(),
}
}
}