refactor(hugrv2)!: combine TypeEnum with Term, no RV parametrization#2895
refactor(hugrv2)!: combine TypeEnum with Term, no RV parametrization#2895
Conversation
…erm::List, mangle_name, skip simple_alias
Merging this PR will degrade performance by 40.19%
Performance Changes
Comparing Footnotes
|
Codecov Report❌ Patch coverage is Additional details and impacted files@@ Coverage Diff @@
## main #2895 +/- ##
==========================================
+ Coverage 83.76% 83.80% +0.04%
==========================================
Files 267 266 -1
Lines 52594 52953 +359
Branches 46533 46892 +359
==========================================
+ Hits 44053 44379 +326
+ Misses 6313 6289 -24
- Partials 2228 2285 +57
Flags with carried forward coverage won't be shown. Click here to find out more. ☔ View full report in Codecov by Sentry. 🚀 New features to boost your workflow:
|
|
I imagine the performance is due to extra cloning, although most that I remember was in hugr-llvm (!)...if we can identify which bits are causing the problem these can probably be rewritten using |
112b608 to
16b4c5e
Compare
|
This PR contains breaking changes to the public Rust API. cargo-semver-checks summary |
| Term::Tuple(elems) => TermSer::TypeArg(TypeArgSer::Tuple { elems }), | ||
| Term::Variable(v) => TermSer::TypeArg(TypeArgSer::Variable { v }), | ||
| Term::Variable(v) => { | ||
| TermSer::TypeArg(if matches!(&*v.cached_decl, Term::RuntimeType(_)) { |
There was a problem hiding this comment.
The need for this complex clause here (it is needed!) only showed up by unexpected changes in the json definition of std_extensions, not any unit test :-(...I'm not sure why
cqc-alec
left a comment
There was a problem hiding this comment.
Thanks @acl-cqc . Have had a general look over this and it looks good to me!
Regarding your questions:
- Does
Kindhave a technical meaning? What would you renameRuntimeTypeto? (I guessTypeType?) In any case I think the docstring forTermshould be expanded, as its current form ("A term in the language of static parameters in HUGR") is rather unclear, at least to me. - Suggest combining these error types, either as a pre- or post-PR (I think this PR is big enough already without adding more changes).
- Probably worth trying (maybe as a follow-up PR).
- Seems like a good idea (perhaps as a follow-up PR).
| // or some static version of this? | ||
| RuntimeExtension(CustomType), |
There was a problem hiding this comment.
needs a #[display] incantation
Term::Runtime(Type), addTerm::RuntimeFunction(FuncValueType),Term::RuntimeSum(SumType)andTerm::RuntimeExtension(CustomType)and removeTypeEnum. That is, runtime types are now just variants ofTerm.Typenow just wraps aTerm, but guarantees by construction that the Term inside it represents a single runtime type. (There is no way to bypass this; there isTryFrom<Term> for Type; there are utility constructors onTypethat takeTypes thus preserving the invariant - the samenew_extension,new_tuple,new_sum,new_functionas before).TypeRowRVwraps a Term, but guarantees it represents a list of types (of perhaps unknown length). That is, it could be aTerm::List(whose elements are single types), or aTerm::Variable(a "row variable" i.e. ranging over lists of types, of unknown length), or aTerm::ListConcat(whose elements are one of these three). Again there are utility constructors preserving the invariant.new+try_new+new_uncheckedconstructors, removed in that commit). However I think with a few nifty TypeRowRV conversions and methods (just_row_varandconcat) the wrapper-struct is easier to use as well as giving more static checking.TypeRowremains as a list ofTypes, i.e. whose length/number-of-types is knownTypeRV. It never had a consistent meaning: it was sometimes a type, and sometimes a list. Also removetrait MaybeRV,enum NoRVandstruct RowVariable.Thus, although the new system offers less Rust-compile-time checking, there is still a reasonable amount, and it's more principled now ;)
Along the way,
Type::as_type_enumwithimpl Deref<Target=Term> for Type, similarly for TypeRowRVtrait Substitutablewrapping the substitute/validate methods, this is used to maintain parametrization of (Poly/)FuncTypeBase over TypeRow or TypeRowRV. Kept hidden as substitute/validate were not public.TODO/To-consider, reviewers' thoughts requested:
Term::XXXType->Term::XXXKindandTerm::RuntimeXXX->Term::XXXType. (ExceptTerm::RuntimeType->Term::TypeKind.) Unclear whether to do this before/after/in this PR..map_err(SignatureError::from)?to convert from TermTypeError :(. It is tempting to combine these two errors (at the least, there are a few other constructors in SignatureError that look redundant i.e. also in TermTypeError!)....sadly Rust won't allowimpl <T: From<SignatureError>> From<TermTypeError> for Twhich would make thesemap_errs go away. Should I do this as a preliminary PR, in here, as a followup?? Any other ideas?TypeintoSumType::General(via a checked struct - prior to 0ac2b53 there was such, called GeneralSum, so we could reintroduce that and add the bound there). Leaving for now but what do reviewers think?TypeRowRV::new_spliced(IntoIterator<Item=Term>)that checks each Term is either a type or a list of types (and panics if not....ok could also havetry_new_spliced), and then assembles the appropriate lists/concats. Might be a bit easier than the currentjust_row_var,concat,from([Type])but would not give as good static (Rust-compile-time) checking....(commit 68fba45 shows this done for FuncValueType whereas here/now it would be for TypeRowRV, i.e. instead ofjust_row_var/concat). Thoughts?BREAKING CHANGE:
TypeEnumandTypeRVare no more - useTerm.RowVariable,MaybeRVetc. are gone - use appropriate term types and variables.TypeandTypeRowRVmerely wrapTermwith invariants.