It seemed appropriate to post this today. Did this while learning lisp about two years ago. Nothing special, a pretty straight forward implementation of the original LISP paper written while reading the paper, basically.
It's difficult to describe the feeling when it clicks and the eval function comes together. All of the complexity of writing a language and an interpreter, reduced to what is basically one function that fits in a page. That is mind blowing.
Edit: I realised this works as a homage to Dennis Richie as well, as it's written in C. I did use glib for some support functions, other than that it's ANSI C.
It's not quite finished (and it's patterned after scheme rather than lisp, but that's close enough) but it runs the towers of Hanoi sucessfully. Lots of stuff still missing, tail call optimization, gc and a whole bunch of other must haves. There are likely lots of bugs too and things that don't work the way they should such as the '.
My understanding of the language is still patchy enough that it probably doesn't work in the way you expect it if you are a schemer.
One of these days I hope to do a proper job of finishing it (too much stuff to do) and do a write-up on it.
Writing this helped me tremendously in understanding the lisp family of languages.
Until I went through it, I'd mostly just played with Haskell for Project Euler and other small problems. That tutorial really helped get the feel for larger projects in the language.
But at the same time, it shows off some of the elegance of lisp. It's simple enough that you can implement it as a beginner tutorial, but the end result is a surprisingly solid language.
One of the beauties of lisp is how much is possible just from some simple building blocks. That tutorial did an excellent job displaying it from the side of a language implementer rather than a language user.
Thanks a ton for it, it was really a pleasure to use.
Thanks a bunch for that tutorial! It demystified language implementation and taught me a little Haskell along the way. Oh and showed me the beauty of parser combinators.
I remember seeing your tutorial before and thinking it looked like a great exercise. Do you think it would be worthwhile for someone with a moderate Haskell background who wants to learn some Scheme? Or is it best to go into it the other way round?
I think it might be quicker to read some Scheme programs to get a feel for the language. It's usually harder to understand exactly what a program is doing by looking at the source code than it is to look at the output of the program and figure out how it got there. (This is also why I always ask for demos and changelist descriptions that explain the intent of the change when I do code reviews at work.)
Some time, it might be fun to write a Haskell interpreter in Scheme. :-) There're all sorts of cool challenges involving type inference there.
I never got macros to work :( Still, the basics like lambdas do work.
The really cute bit is that it lets you include <script language="scheme"> blocks in your html and actually parses them. It even lets the scheme code access JavaScript objects using some special syntax.
There's one of those blocks in the source of the page; be sure to check it out.
Implemented in C++. Makes extensive use of C++ features and libraries to produce a lot of lisp in a small number of LOC. Includes exceptions, a full numeric tower (including unlimited-precision floats, courtesy of CLN), vectors and dictionaries (courtesy of the STL), and dynamic code loading (courtesy of dlopen). Uses the Boehm GC. Still buggy, not quite ready for prime time, but it does work.
It's an incomplete toy level Scheme subset with bugs, but it has HTML5 canvas support and some cute features like showing you the progress of the VM instead of hanging the browser, and call/cc. I'd like to finish it someday.
Initially started off as a toy implementation and eventually fleshed out into a pretty nice system, used in a production environment for several years as a DSL in a perl based system.
I started this a few weeks ago after rereading sicp chapter 4 and realizing that it made more sense this time around.
Some of the most fun I've ever had with programming (though I haven't been doing it very long). Never got around to doing the cool stuff at the end of SICP though, I should really get on that...
I've been working on a MACLISP interpreter based on 80's manual I found on my fathers bookshelf. It's quite fun working backward, and seeing how the dialect influenced modern lisp.
literally just wrote this last night and pushed it live this morning before hearing the news. I had just changed my gmail status to "season of the lisp" as I go through a seasonal fixation w/ lisp every year starting in october - when an old colleague messaged me to inform me of his passing.
Lisp implemented in Java. Fairly complete set of datatypes and functions, but no objects. Has been available for 10 years. http://jatha.sourceforge.net/
Mine is in Python with several usual and some less usual influences: John McCarthy "Recursive Functions of..." by way of Paul Graham "The Roots of Lisp"; Peter Norvig "(How to Write..." and tail recursion from his "(An ((Even Better)..."; quoted-printable encoding of characters; Wikipedia & Knuth's enthusiasm for the balanced ternary number base. I have gone a very short way to start translating Lisp programs to Python code. Also I have gone a very short way to do relevant proofs in Coq in the manner of Benjamin C. Pierce, et al. "Software Foundations". My notions are to implement the Calculus of Constructions in the simplified form found in Claudio S. Coen, "Mathematical Libraries as Proof Assistant Environments", and natural deduction on top of that. And a TR SECD machine. Oh, and algorithms from Artificial Intelligence: A Modern Approach. And a pony...
http://github.com/minopret/minopret-lisp
My scheme implementation, written in C a year ago, just for fun. Took me a week or so, 942 C LoC.
From the README: "lexical scoping, Fixnum and floating point arithmetics, unhygienic macros, tail-call elimination, reentrant continuations, and automatic memory management (garbage collection)".
Implementing a tiny Lisp is an exercise in learning to be a better programmer by teaching yourself how language implementations work. Creating a patch for someone else's Lisp interpreter is not a reasonable substitute.
Edit: I realised this works as a homage to Dennis Richie as well, as it's written in C. I did use glib for some support functions, other than that it's ANSI C.
R.I.P.