[Author Prev][Author Next][Thread Prev][Thread Next][Author Index][Thread Index]
[pygame] Whirl Interpreter
- To: pygame-users@xxxxxxxx
- Subject: [pygame] Whirl Interpreter
- From: Luke Paireepinart <rabidpoobear@xxxxxxxxx>
- Date: Mon, 22 May 2006 01:30:06 -0500
- Delivered-to: archiver@seul.org
- Delivered-to: pygame-users-outgoing@seul.org
- Delivered-to: pygame-users@seul.org
- Delivery-date: Mon, 22 May 2006 02:30:29 -0400
- Domainkey-signature: a=rsa-sha1; q=dns; c=nofws; s=beta; d=gmail.com; h=received:message-id:date:from:user-agent:mime-version:to:subject:content-type; b=YUfv3Vzw8xZicEfadR6CAEvZoW7bdu5xh7dlVFeL9Sh2GELcHcYhIgwaVGLLXbqeqlktpKUMMvmtvad8PTCF/s4K0PyJsuBnCZpvhvprFSFNHSJ7LnLRFhB2LfO0KDLuur0lcUwXfgT3gp9mb+aTIEqcdQZwzPXaSgZrgUNRFH4=
- Reply-to: pygame-users@xxxxxxxx
- Sender: owner-pygame-users@xxxxxxxx
- User-agent: Thunderbird 1.5.0.2 (Windows/20060308)
Hey everyone.
I just got finished writing an interpreter for the esoteric language
called Whirl (linky: http://www.bigzaphod.org/whirl/ )
I was thinking about writing a graphical version of the interpreter as well.
Does anyone see anything wrong with my code that would be more easily
done a different way before
I start writing the graphical version?
Just wondering if I have developed any bad coding habits I didn't know
about.
Be honest please!
-Luke
#!/usr/local/bin/python
"""
Whirlinterp.py - an interpreter for the esoteric language Whirl (found at http://bigzaphod.org/whirl)
Copyright (C) 2006 Luke Paireepinart
This program is free software; you can redistribute it and/or
modify it under the terms of the GNU General Public License
as published by the Free Software Foundation; either version 2
of the License, or (at your option) any later version.
This program is distributed in the hope that it will be useful,
but WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
GNU General Public License for more details.
You should have received a copy of the GNU General Public License
along with this program; if not, write to the Free Software
Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
"""
import sys
global OPS,MEMORY,PC, MC
OPS = []
PC = 0
MC = 0
MEMORY = [0]
class OpRing:
def __init__(self):
self.currentop = 0
self.opring = ["NOOP","EXIT","ONE","ZERO","LOAD","STORE","PADD","DADD","LOGIC","IF","INTIO","ASCIO"]
self.val = 0
self.direction = 0
pass
def ROTATE(s):
if s.direction == 0:
s.currentop = (s.currentop + 1) % 12
elif s.direction == 1:
s.currentop = (s.currentop -1) % 12
else:
print "Error in ROTATE. self.direction not 0/1."
def FLIP(s):
s.direction = s.direction ^ 1
return s.direction
def EXEC(self):
global MEMORY,MC,PC,OPS
t = self.opring[self.currentop]
if t == "NOOP":
pass
elif t == "EXIT":
return "EXIT"
elif t == "ONE":
self.val = 1
elif t == "ZERO":
self.val = 0
elif t == "LOAD":
self.val = MEMORY[MC]
elif t == "STORE":
MEMORY[MC] = self.val
elif t == "PADD":
PC += self.val - 1
if PC < -1:
PC = -1
elif len(OPS) < PC:
return "EXIT"
elif t == "DADD":
MC += self.val
if MC < 0:
MC = 0
while len(MEMORY) <= MC:
MEMORY.append(0)
elif t == "LOGIC":
if MEMORY[MC] == 0:
self.val = 0
else:
self.val = (self.val and 1)
elif t == "IF":
if MEMORY[MC] != 0:
PC += (self.val-1)
if PC < -1:
PC = -1
elif len(OPS) < PC:
return "EXIT"
elif t == "INTIO":
if self.val == 0:
MEMORY[MC] = int(raw_input("Please enter an integer: "))
else:
return MEMORY[MC]
elif t == "ASCIO":
if self.val == 0:
MEMORY[MC] = raw_input("Please enter a character: ")[0]
else:
try:
return chr(MEMORY[MC])
except TypeError:
return MEMORY[MC]
def GETCURRENTOP(self):
return self.opring[self.currentop]
class MathRing:
global MEMORY,PC, MC
def __init__(self):
self.opring = ["NOOP","LOAD","STORE","ADD","MULT","DIV","ZERO","<",">","=","NOT","NEG"]
self.val = 0
self.currentop = 0
self.direction = 0
def ROTATE(s):
if s.direction == 0:
s.currentop = (s.currentop + 1) % 12
elif s.direction == 1:
s.currentop = (s.currentop -1) % 12
else:
print "Error in ROTATE. self.direction not 0/1."
def FLIP(s):
s.direction = s.direction ^ 1
return s.direction
def EXEC(self):
t = self.opring[self.currentop]
if t == "NOOP":
pass
elif t == "LOAD":
self.val = MEMORY[MC]
elif t == "STORE":
MEMORY[MC] = self.val
elif t == "ADD":
self.val += MEMORY[MC]
elif t == "MULT":
self.val *= MEMORY[MC]
elif t == "DIV":
if MEMORY[MC] != 0:
self.val /= MEMORY[MC]
else:
print "Attempted to divide by zero. Value in Math Ring unchanged."
elif t == "ZERO":
self.val = 0
elif t == "<":
self.val = (self.val < MEMORY[MC])
elif t == ">":
self.val = (self.val > MEMORY[MC])
elif t == "=":
self.val = (self.val == MEMORY[MC])
elif t == "NOT":
self.val = (self.val == 0)
elif t == "NEG":
self.val *= -1
def main():
global OPS,MEMORY,PC, MC
opring = OpRing()
mathring = MathRing()
rings = {"OPRING":opring,"MATHRING":mathring}
if len(sys.argv) < 2:
print "Must specify a filename as the argument. eg: python whirlinterp.py filename.txt"
raise SystemExit
filename = sys.argv[1]
f = file(filename,'r')
text = f.readlines()
f.close()
for line in text:
for char in line:
if char in ['0','1']:
OPS.append(char)
previousop = 3
current = "OPRING"
outputtext = ""
while PC < len(OPS):
if OPS[PC] == "0":
rings[current].FLIP()
if previousop == 0:
text = rings[current].EXEC()
if text == "EXIT":
print outputtext
raise SystemExit
elif text != None:
try:
sys.stdout.write(text)
except TypeError:
sys.stdout.write(str(text))
if current == "OPRING":
current = "MATHRING"
elif current == "MATHRING":
current = "OPRING"
previousop = 1
else:
previousop = 0
elif OPS[PC] == "1":
rings[current].ROTATE()
previousop = 1
PC += 1
print outputtext
if __name__ == "__main__":
main()