Created
September 23, 2016 00:44
-
-
Save mr1337357/cdf903c19eb68f9c5328e9f121b3325b to your computer and use it in GitHub Desktop.
language
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
def dup ( a | | |
| a a ) | |
def drop ( a | | |
| ) | |
def swap ( a b | | |
| a b ) | |
def * ( a b | | |
mac cpy ( <b if <a <b -1 + >b cpy end ) | |
mac sum ( count -1 + if + sum end ) | |
cpy sum >a | |
| a ) | |
mac not ( | |
0 = | |
) |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
from collections import deque | |
import os | |
from copy import copy | |
class scope: | |
def __init__(self,parent=None): | |
self.parent=parent | |
self.content={} | |
def __getitem__(self,name): | |
if name in self.content: | |
return self.content[name] | |
if self.parent and name in self.parent: | |
return self.parent[name] | |
return None | |
def __setitem__(self,name,value): | |
self.content[name] = value | |
def __contains__(self,name): | |
if name in self.content or self.parent and name in self.parent: | |
return True | |
return False | |
def __repr__(self): | |
out = '{\n' | |
out += '\n'.join([key+': '+repr(self.content[key]) for key in self.content]) | |
out += '\n}\n => \n' | |
out += repr(self.parent) | |
return out | |
globalvars = scope() | |
globalstack = [] | |
class mac: | |
def __init__(self,words): | |
if words.popleft() != '(': | |
raise Exception('no macro contents') | |
self.code=deque() | |
while words[0] != ')': | |
self.code.appendleft(words.popleft()) | |
words.popleft() | |
def __call__(self,context,stack): | |
interpret(reversed(self.code),context,stack) | |
def __repr__(self): | |
out = 'mac ( ' | |
out += ' '.join([repr(code) for code in self.code]) | |
out += ' )' | |
return out | |
class fn: | |
def __init__(self,words): | |
if words.popleft() != '(': | |
raise Exception('no function contents') | |
self.args=[] | |
self.code=deque() | |
self.rets=[] | |
while words[0] != '|': | |
self.args.append(words.popleft()) | |
words.popleft() | |
while words[0] != '|': | |
self.code.append(words.popleft()) | |
words.popleft() | |
while words[0] != ')': | |
self.rets.append(words.popleft()) | |
words.popleft() | |
def __call__(self,context,stack): | |
newcontext=scope(context) | |
newstack = [] | |
for name in self.args: | |
newcontext[name]=stack.pop() | |
interpret(copy(self.code),newcontext,newstack) | |
for name in self.rets: | |
stack.append(newcontext[name]) | |
def __repr__(self): | |
out = 'fn ( ' | |
out += ' '.join([repr(arg) for arg in self.args]) | |
out += ' | ' | |
out += ' '.join([repr(code) for code in self.code]) | |
out += ' | ' | |
out += ' '.join([repr(ret) for ret in self.rets]) | |
out += ' )' | |
return out | |
def interpret(queue,context,stack): | |
if isinstance(queue,str): | |
queue=deque(queue.split()) | |
while len(queue): | |
word = queue.popleft() | |
if word == 'def': | |
name = queue.popleft() | |
context[name]=fn(queue) | |
elif word == 'mac': | |
name = queue.popleft() | |
context[name]=mac(queue) | |
elif word == 'if': | |
if stack.pop() == 0: | |
while queue.popleft() != 'end': | |
pass | |
elif word[0] == '<': | |
stack.append(context[word[1:]]) | |
elif word[0] == '>': | |
context[word[1:]] = stack.pop() | |
elif word in context: | |
val = context[word] | |
if isinstance(val,mac): | |
queue.extendleft(val.code) | |
elif callable(val): | |
val(context,stack) | |
try: | |
stack.append(int(word)) | |
except: | |
pass | |
def printfcn(context,stack): | |
print stack.pop() | |
def dump(context,stack): | |
print '[', | |
for item in stack: | |
print item, | |
print ']' | |
#print context | |
globalvars['.'] = printfcn | |
globalvars['='] = lambda context,stack: stack.append(1 if stack.pop() == stack.pop() else 0) | |
globalvars['+'] = lambda context,stack: stack.append(stack.pop()+stack.pop()) | |
globalvars['count'] = lambda context,stack: stack.append(len(stack)) | |
globalvars['dump'] = dump | |
#interpret('def dup ( a | | a a ) def swap ( a b | | a b )',globalvars,globalstack) | |
try: | |
with open(os.path.expanduser('~/.lang.init'),'r') as initfile: | |
interpret(' '.join(initfile.readlines()),globalvars,globalstack) | |
except Exception as e: | |
print 'no initfile' + repr(e) | |
pass | |
import sys | |
if len(sys.argv) > 1: | |
try: | |
with open(sys.argv[1],'r') as infile: | |
interpret(' '.join(infile.readlines()),globalvars,globalstack) | |
except: | |
pass | |
else: | |
while True: | |
interpret(raw_input('LANG: '),globalvars,globalstack) | |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment