Skip to content

Instantly share code, notes, and snippets.

@SamuraiT
Created December 10, 2014 00:57
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save SamuraiT/08c11293f4ff7f7fc369 to your computer and use it in GitHub Desktop.
Save SamuraiT/08c11293f4ff7f7fc369 to your computer and use it in GitHub Desktop.
simple lisp interpreter
# coding: utf-8
Env = dict
Symbol = str
List = list
Number = (int, float)
def tokenize(chars):
return chars.replace('(', ' ( ').replace(')', ' ) ').split()
def parse(program):
return read_from_tokens(tokenize(program))
def read_from_tokens(tokens):
if len(tokens) == 0: raise SyntaxError("unexpected EOF while reading")
token = tokens.pop(0)
if token == '(':
L = []
while tokens[0] != ')':
L.append(read_from_tokens(tokens))
#print(L)
tokens.pop(0) # pop off ')'
return L
elif token == ')': raise SyntaxError('unexpected')
else: return atom(token)
def atom(token):
try: return int(token)
except ValueError:
try: return float(token)
except ValueError:
return Symbol(token)
def starndard_env():
import operator as op
env = Env()
env.update({
'+': op.add,
'-': op.sub,
'*': op.mul,
'/': op.truediv,
'>': op.gt,
'<':op.lt,
'>=': op.ge,
'<=': op.le,
'=': op.eq,
})
return env
global_env = starndard_env()
global_env
def eval(x, env=global_env):
if isinstance(x, Symbol): return env.find(x)[x]
elif not isinstance(x, List): return x
else:
proc = eval(x[0], env)
args = [eval(arg, env) for arg in x[1:]]
return proc(*args)
def repl(prompt="(scheme)> "):
while True:
val = eval(parse(input(prompt)))
if val is not None:
print(val)
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment