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

Support closure on (fn) #20

Merged
merged 2 commits into from
Dec 31, 2015
Merged

Support closure on (fn) #20

merged 2 commits into from
Dec 31, 2015

Conversation

chrhlnd
Copy link
Contributor

@chrhlnd chrhlnd commented Dec 20, 2015

Ok I took a stab at this, the original script runs now, also (def val (fn ) works as a callable too.

1st commit is the meat of the real change, 2nd commit is go fmt on everything.

@zhemao
Copy link
Owner

zhemao commented Dec 21, 2015

Hmm, I think cloning the entire environment might be a little too heavyweight. The only thing that needs to be switched out is the scope stack. Now that I think about it, I think the way I designed scoping was a bit incorrect. The parent scope of a function's top-level scope should be the global scope (or the scope of the function it was defined in, in the case of closures). When the function is defined, an object saving its enclosing scope hierarchy should be placed on the stack. For regular functions, this object could just be null or empty. When the function is called, the current scope hierarchy should be saved (on a stack of scope stacks), and the one for the function should be popped off the argument stack. A new scope is then added for the called function and the execution should continue from the beginning of the function bytecode. Do you think you could implement it that way? Otherwise, I'll take a stab at it when I have time.

@chrhlnd
Copy link
Contributor Author

chrhlnd commented Dec 21, 2015

Hmm well the references to data would have to be preserved too. The 'fun' parameter being used in the closure defined in filter (being passed to foldl), is referencing the data from the filter call but its execution won't necessarily be in the current stack. It is in this case; but the 'fn' value could be returned and passed around, then applied at some other point.

@zhemao
Copy link
Owner

zhemao commented Dec 21, 2015

You're right. In that case, we should bundle the scope stack reference into the function object.

@chrhlnd
Copy link
Contributor Author

chrhlnd commented Dec 27, 2015

Ok I've re-done it, to build up resolvable scope at execute of the Fn. Some work is in vm.go and more is in environment.go

Also squashed the commits down to 1.

@chrhlnd chrhlnd force-pushed the master branch 2 times, most recently from 9e7ad8f to 4a44dd2 Compare December 28, 2015 19:11
@chrhlnd chrhlnd force-pushed the master branch 2 times, most recently from 9e7ad8f to 0b30e67 Compare December 28, 2015 19:24
@chrhlnd
Copy link
Contributor Author

chrhlnd commented Dec 30, 2015

One more cleanup, to avoid capturing globals needlessly.

@zhemao zhemao merged commit 8b81072 into zhemao:master Dec 31, 2015
@zhemao
Copy link
Owner

zhemao commented Dec 31, 2015

Looks good. I added some additional tests and merged into master. Thanks for your help.

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