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

Preliminary implementation of let-bindings. #133

Merged
merged 3 commits into from
Sep 9, 2018

Conversation

boomshroom
Copy link
Contributor

This should help going forward. There are several things this does not cover which will needed to be worked on in the future, namely recursion and mutual recursion, as well as type inference. let x : I32; x = 5; in x does not work in this version.

Another huge thing missing right now are tests. At the very least, all previous tests seem to pass and manual checking in the repl does what's expected.

This also includes a few refactors such as pulling code out of the module translation function to reuse for let-bindings and possibly in the future, records. In addition, I added InternalError::Unimplemented{ feat: String } to make it easier to stub behavior without panicking.

Copy link
Member

@brendanzab brendanzab left a comment

Choose a reason for hiding this comment

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

Sorry for all the comments - this is really exciting! Thanks for working on it! I'll try to think up some test cases for us to try!

@@ -24,6 +24,8 @@ pub enum InternalError {
ProjectedOnNonExistentField { label: syntax::Label },
#[fail(display = "No patterns matched the given expression.")]
NoPatternsApplicable,
#[fail(display = "Feature unimplemented: {}", feat)]
Unimplemented{ feat: String }
Copy link
Member

Choose a reason for hiding this comment

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

SO GOOD! Thanks!

@@ -356,7 +356,7 @@ where
let raw_ty_fields = raw_ty_fields.unnest();

if raw_fields.len() != raw_ty_fields.len() {
unimplemented!();
return Err(TypeError::Internal(InternalError::Unimplemented{feat: "record size mismatch. (change to RecordSizeMismatch)".to_string()}));
Copy link
Member

Choose a reason for hiding this comment

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

Do you have rustfmt running? I try to have this on by default. Also we can probably remove this whole check because it is already covered in the check you added in #130! 😄

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 made that return an error just in case. It should never happen with the previous check, but you can never be too careful.

@@ -576,6 +576,32 @@ where
))
},

// I-LET
raw::Term::Let(_, ref raw_scope) => {
//return Err(TypeError::Internal(InternalError::Unimplemented{feat: "let-binding".to_string()}));
Copy link
Member

Choose a reason for hiding this comment

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

Stray comment here!

@@ -576,6 +576,32 @@ where
))
},

// I-LET
Copy link
Member

Choose a reason for hiding this comment

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

This refers to an inference rule in theory.md that we'll have to update. It's a bit icky to work with (a bunch of mathjax) so I can update it in a separate PR if you like. I have some ideas for overhauling the specification website - see #109 for that!

@@ -190,6 +190,7 @@ pub enum Term {
Case(ByteSpan, RcTerm, Vec<Scope<RcPattern, RcTerm>>),
/// Array literals
Array(ByteSpan, Vec<RcTerm>),
Let(ByteSpan, Scope<(Binder<String>, Embed<(RcTerm, RcTerm)>), RcTerm>)
Copy link
Member

Choose a reason for hiding this comment

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

Missing a doc comment here

items: &[concrete::Item],
body: &concrete::Term,
) -> raw::RcTerm {
//unimplemented!("let bindings");
Copy link
Member

Choose a reason for hiding this comment

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

Stray comment

let hole = raw::RcTerm::from(raw::Term::Hole(ByteSpan::default()));

items.into_iter().rev().fold(body, |acc, item| match item {
raw::Item::Declaration{..} => acc, // TODO Let declarations
Copy link
Member

Choose a reason for hiding this comment

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

Super obsessive nit-pick: I try to use a colon in TODOs, eg: // TODO: let declarations

Copy link
Member

Choose a reason for hiding this comment

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

We might want to reuse the module level desugaring for this, but I'm cool with keeping this PR simpler.

@@ -189,51 +247,13 @@ fn desugar_record(

impl Desugar<raw::Module> for concrete::Module {
fn desugar(&self, env: &DesugarEnv) -> raw::Module {
let mut env = env.clone();
//let mut env = env.clone();
Copy link
Member

Choose a reason for hiding this comment

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

Stray comment

@@ -391,6 +391,7 @@ fn resugar_term(term: &core::Term, prec: Prec) -> concrete::Term {
vec![resugar_term(arg, Prec::NO_WRAP)], // TODO
),
),
core::Term::Let(ref _scope) => unimplemented!(),//resugar_let(scope, prec),
Copy link
Member

Choose a reason for hiding this comment

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

Stray comment here - did you want to implement this in this PR, or later? I'm cool if you want to defer it!

@boomshroom
Copy link
Contributor Author

Thanks for the comments. I wrote the changes then went to sleep planning to fix things up, but forgot when I decided not to bother with tests.

@boomshroom
Copy link
Contributor Author

Seems like cargo fmt changed more than my changes.

@brendanzab
Copy link
Member

brendanzab commented Sep 7, 2018

Yeah, perfectly fine if rustfmt changes more things. I wonder if it is because I'm using the nightly version... 🤔

@brendanzab
Copy link
Member

woww, the stable version of rustfmt actually looks quite ugly compared to nightly 😅

@brendanzab
Copy link
Member

Would you be able to rebase this branch onto https://github.com/brendanzab/pikelet/tree/let-binding - I ran the nightly rustfmt on it, and added some tests.

@boomshroom boomshroom force-pushed the let-binding branch 2 times, most recently from d41a9a7 to c073242 Compare September 9, 2018 01:11
@brendanzab brendanzab merged commit 6a0adb8 into pikelet-lang:master Sep 9, 2018
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

Successfully merging this pull request may close these issues.

2 participants