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

tomlisp: Tom's Obvious, Minimal Lisp (by Steve) #159

Merged
merged 21 commits into from Aug 22, 2021
Merged

Conversation

steveklabnik
Copy link
Contributor

Code is data. Data is code. What's a popular data format? TOML. So why can't
TOML be code?

image
image

tomlisp is a lisp, but with TOML syntax. Here is "Hello world" im tomlisp:

# hello, world!
main = "hello, world!"

The main key's value is your program, which will be executed, and the final
value printed to the screen before the interpreter exits.

This jam's theme is "first-class comments." When asked to elaborate, jt said:

there are many ways to interpret "first-class", all of them are valid

I've been on an airplane before. I know what "first class" means. It means that
they're at the front, and there's a limited amount of space. So in tomlisp,
your TOML files must start with a comment. This is the only place a comment is
allowed to live. And you get 20 characters to work with. If you use more
than that, your program will be rejected.

Compiling and running

It's a Rust project, so install Rust. Then use cargo run:

$ cargo run samples\langauge2.toml

The samples directory contains a few sample programs.

Stuff that's supported

  • All TOML values
  • if: takes a test, the true value, and the false value
  • begin: evalutes each value in turn
  • define: saves a value in the environment
  • lambda: creates a closure
  • * and +: multiplies or adds all numbers together
  • pi: you know what this is already

Why aren't other things supported?

Because this is a 48 hour jam and I am getting old and tired. You don't need
to divide anyway.

Known bugs

Because TOML doesn't support bare words, symbols are strings, and strings are
symbols. Currently, this means that when evaluating a string, it will attempt
to resolve it as a symbol first, and if that fails, resolves it as a literal
string instead. This means you can't have string literals with the same name
as anything you've defined in the environment. This could be resolved if I cared
enough to fix it, but this is just a fun jam. I'd probably make strings that
start with $ symbols or something.

Acknowledgements

Thank you to everyone who came by my
stream
. The only idea I had coming
into the jam was "homoiconic TOML," and the stream was invaluable in making me
realize that I was just writing a Lisp for real rather than something lisp-ish
and so I should just simplify what I was doing into a Lisp. Lots of great
brainstorming and conversation in there. I wish I had the energy to do it the
whole time.

Whenever I need to knock out a little Lisp, I turn to the classic article by
Peter Norvig, "(How to Write a (Lisp) Interpreter (in
Python))"
. I once again turned to it for this
project. This is why pi is in there, for example.

Additionally, "Risp (in (Rust) (Lisp))" by Stepan
Parunashvili was useful. This is an implementation of Norvig's Lisp in Rust, and
our implementations end up being pretty similar, first of all because we're
working on the same source material, but also because I shamelessly looked at
his code when I felt stuck. Any good things that look similar to his stuff is
due to him, not me :) One extremely notable difference is that he does real
error handling in his code, while I just panic when I hit a problem.

@jntrnr jntrnr merged commit b57d730 into langjam:main Aug 22, 2021
BenJilks pushed a commit to BenJilks/jam0001 that referenced this pull request Aug 25, 2021
* Hello, world

* about to do weird recursion stuff

* user defined functions work

* refactor to vm struct

* we have comments

* refcell crimes

* syntax 2.0

* Redo with toml crate

* lol, + exists but does not work

* + works lol

* handle lists of strings

* okay list of strings doesn't actually make sense so

* can use other types now

* fmt time

* more stuff

* if

* define works

* fmt time

* first class 🤣

* lambda works

* we're done here
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.

None yet

2 participants