5 ms·
RE: What's so cool about Scheme? (2003)
- Ono-Sendai 11y agoI like the koan. I was working on a closure implementation this weekend. When wondering how to clean up the captured variables in the closure, I realised that the most natural way (to me at least) is effectively to store a 'destructor' pointer in the closure, which is very similar to the idea of a destructors and virtual methods in c++. As such I was enlightened :)
- prakashk 11y agohttp://www.c2.com/cgi/wiki?ClosuresAndObjectsAreEquivalent http://www.c2.com/cgi/wiki?ClosuresAndObjectsAreEquivalent
- brudgers 11y agoMaster, I have heard Scheme is a poor man's Javascript.
- pmelendez 11y agoActually it's the other way around. Javascript was created because the author couldn't use Scheme. The first comment of https://brendaneich.com/tag/history/ https://brendaneich.com/tag/history/ have this perl: "As I’ve often said, and as others at Netscape can confirm, I was recruited to Netscape with the promise of “doing Scheme” in the browser. " Edit: After a second read, I get now that you were being sarcastic about the koan. Silly me, I don't get those over the net :)
- martin1975 11y agoevery time someone gets into how cool functional languages are, for some reason I always think of this - http://databaseanswers.org/data_models/father_of_all_models/index.htm http://databaseanswers.org/data_models/father_of_all_models/...
- pmelendez 11y agoEAVs are awesome :) Once upon a time, I didn't know about their existence and didn't have anyone to point me in that direction, and I converged in pretty much the same thing when I was asked to implement an automatic forms generator from data. It feels silly when you just discover something cool that is old news.
- jdmichal 11y agoI felt the same way having rediscovered tries writing a word-search algorithm to cheat at Scrabble. (Hey, don't judge me!) "I wonder what would happen if I made a binary search tree, except it has a branch for each letter..."
- brudgers 11y agoNot trying to be sarcastic. Scheme doesn't run in the browser and lacks tooling for readily manipulating the DOM...at least typically. Lisp in the browser has been much on my mind as I've been trying to get a handle on Clojurescript. It's a poor atom-blaster that doesn't point both ways -- Hober Mallow
- pmelendez 11y ago>"Scheme doesn't run in the browser and lacks tooling for readily manipulating the DOM" Meh... [1][2][3][4] [1] http://www.biwascheme.org/ http://www.biwascheme.org/ [2] https://github.com/jcoglan/fargo https://github.com/jcoglan/fargo [3] https://www.hashcollision.org/whalesong/ https://www.hashcollision.org/whalesong/ [4] http://wiki.call-cc.org/eggref/4/spock http://wiki.call-cc.org/eggref/4/spock
- brudgers 11y agoI qualified my statement with "typically". Here's some whalesong: ;; Set the background green, and show some content ;; on the browser. (void (call-method body "css" "background-color" "lightgreen")) (void (call-method ($ "<h1>Hello World</h1>") "appendTo" body)) I love Racket. Yet, I'm not enough of a masochist to use Whalesong instead of Javascript just to prove my love.
- discreteevent 11y agoMafribe had an interesting comment here: https://news.ycombinator.com/item?id=9506195 https://news.ycombinator.com/item?id=9506195 Milner showed how to encode the lambda calculus as message passing but "parallel computation has no 'good' encoding into functional computation". So message passing is fundamental. Plus in the end there are parts of your system that you are going to have to model in this way anyway. e.g. IPC. Personally it helps me psychologically to have a common model for everything even if when I am e.g. composing functions I'm not really thinking about messages.
- Ono-Sendai 11y agoCan you expand on "parallel computation has no 'good' encoding into functional computation"?
- Tobani 11y agoTo be fair I think the same is true of procedural languages. Parallel computation often requires some sort of coordination mechanism, and there are more failure modes. Functional languages often lend them selves to elegant mathematic-looking functions and algorithms with many of the dirtier parts figured out by the compiler. In order to map algorithms to parallel computing for non-trivially parallel problems you'll need things like futures, message passing, etc. that gets you back into specifying the dirtier low-level parts of the algorithm again. Its more idiomatic in a procedural language because your'e doing all of this work all the time any way. It is still a hassle, it just doesn't mess with the "Elegance."
- pdpi 11y agoHave you ever looked at Strategies (or the Par monad) in Haskell? To me, Strategies exemplify some of the stuff you can do with functional languages that are _really_ hard to achieve elsewhere.
- Tobani 11y agoI have seen it before and it is pretty amazing. My comment was mostly in context of the 2003 message. People are finding more and more clever ways of handling this all the time. Par(at least monad-par on hackage) seems to have come around 2011. Really multi-core machines have only been standard for about 10 years now? Before then, multi-processor machines filled more niche roles (Servers, HPC, etc). Now my phone has 4 cores. Parallel computing is becoming more common because all of the code you write will run on a multi-core system. I definitely see how writing multi-threaded code in a lisp in 2003 would have been less savory. Things are definitely better now. Things like Par & Repa can do some amazing things in Haskell. I'm sure there are more some great packages out for scheme that are similar . I don't think we're 100% there yet. Who knows where we'll be in another 10 years?
- melling 11y agoSometime in the next 5 to 10 years, you'll be able to extend Emacs with Scheme: http://emacswiki.org/emacs/GuileEmacs http://emacswiki.org/emacs/GuileEmacs Hopefully, people will build IDE's comparable to IntelliJ with it.
- davexunit 11y agoNot only that, but you'll have an operating system distribution made with Scheme on which to run it: http://git.savannah.gnu.org/cgit/guix.git/tree/gnu/packages/emacs.scm#n153 http://git.savannah.gnu.org/cgit/guix.git/tree/gnu/packages/...
- pmelendez 11y ago>"If all you want to do is e.g. (map somefun mylist), being able to concisely define executable "objects" (closures), inline if necessary, is very useful." It is interesting because this is exactly how C++11 implements lambdas. Still Scheme's closures are more convenient although C++14 is closing the gap.
- frou_dh 11y agoIn my own scheme-esque language, I have tried hooking up extra-concise means not only for lambdas, but for "anonymous macros" too. (Yes, the readability of the resulting code is very suspect. Just experimenting!) # Provide a prefix syntax that constructs a unary procedure from just a body. (extend-parser "^" (mac (x) `(proc (?) ,x))) # Provide a prefix syntax that constructs a unary macro from just a body. (extend-parser "%" (mac (x) `(mac (?) ,x))) # Apply an anonymous macro to 4, resulting in definitions for cad{1,4}r # being generated then evaluated: ( %`(seq ~(map ^(let i (codepoint-count ?) sym (string-to (sprint "ca" ? "r")) `(def ,sym (proc (xs) (ith-element ,i xs)))) (map ^(apply sprint (repeat "d" ?)) (range 1 ?)))) 4) # What ended up being evaluated at the top-level: # (seq (def cadr (proc (xs) (ith-element 1 xs))) # (def caddr (proc (xs) (ith-element 2 xs))) # (def cadddr (proc (xs) (ith-element 3 xs))) # (def caddddr (proc (xs) (ith-element 4 xs))))
- jjtheblunt 11y agoI think you have a mistake in what you wrote, but please correct me if I am wrong. C++11 lambdas which capture free variables by reference can not be returned from a function in which the free variables occur, and be expected to work, because the function's variable (a free variable to the lambda) may no longer refer to memory allocated for use as the variable. That's not true for Scheme. Scheme's underlying implementation of lambda and function call means that true closures are created: if a lambda refers to a variable which is not local to (or a parameter to) the lambda, then that free variable belongs to an environment, whose lifetime isn't delimited by popping a stack and returns, and is therefore still live as long as some closure (or stack activation frame) refers to it. Return of a lambda with free variables will work in Scheme, and can fail in C++11.
- arca_vorago 11y agoFor anyone interested in Scheme, may I suggest taking a look at Racket. It has a very nice IDE, and is growing surprisingly quickly. I admit though there is something about lisp that I just really like (perhaps I'm addicted to parentheses).
- divs1210 11y agoThis post had inspired me to write CljOS[1], an Object System in Clojure mainly because I wanted to write a game engine and had freshly arrived from the Java world. It turned out to be extremely straightforward to map objects to closures. Took <100 lines of documented code! obj.method(& args) => (obj :method & args) I even have a basic 2d sprite-based game engine here[2] (on top of Swing!). [1] https://github.com/divs1210/cljos https://github.com/divs1210/cljos [2] https://github.com/divs1210/bakait https://github.com/divs1210/bakait
- copsarebastards 11y ago> A closure is an object that supports exactly one method: "apply". What's more, this enforces good object-orientation: this is a reimagining of the single-responsibility principle because closures are objects that literally do one thing. Closures also enforce the open-close principle. Once it's closed it's closed. The result is that you get a lot of good OO practices for free.