Parent Directory
|
Revision Log
extracted phase1.py from transform.py
"""
this is curt's initial version of simple.py, as
extracted from transform.py
"""
from transform import Transformer
from compiler.ast import ListComp
from compiler.ast import Discard
from compiler.ast import Function
from compiler import ast
from compiler import pycodegen
global ListCompExpr
class ListCompExpr(ast.Node):
def __init__(self, expr):
self.expr = expr
# takes in the Discard or listComp node and
# sends the appropriate body to comprehend
# to break down the listcomp
def expressListComp(node):
# we were given a Discard node
if isinstance(node.expr, ListComp):
queue = node.expr.quals + [ListCompExpr(node.expr.expr)]
return comprehend(0, queue)
# we were given a ListComp node
elif isinstance(node, ListComp):
queue = node.quals + [ListCompExpr(node.expr)]
return comprehend(1, queue)
else:
return node
# We pass comprehend a 0 if the ListComp is surrounded
# by a Stmt node, and 1 if it is not. We know this
# because a Discard is wrapped in a Stmt, and a print
# call before a ListComp is not wrapped in a Stmt node.
#
# This should return a tree that is syntactically identical
# to a ListComp translated into a for/if AST.
#
def comprehend(int, queue):
"""
do our own walk of the tree and rebuild
using ast.For and ast.If
"""
head, tail = queue[0], queue[1:]
if int == 0:# it was a Discard node
if isinstance(head, ast.ListCompFor):
return ast.For(assign = head.assign,
list = head.list,
body = comprehend(1, head.ifs + tail),
else_ = None)
else:# it was a print node or subsequent calls to comprehend
head, tail = queue[0], queue[1:]
if isinstance(head, ast.ListCompFor):
return ast.Stmt([ast.For(assign = head.assign,
list = head.list,
body = comprehend(1, head.ifs + tail),
else_ = None)])
elif isinstance(head, ast.ListCompIf):
return ast.Stmt([ast.If(tests = [(head.test, comprehend(1, tail))],
else_ = None)])
elif isinstance(head, ListCompExpr):
return ast.Stmt([Discard(head.expr)])
else:
raise "i can't comprehend a %s" % head.__class__.__name__
# HELP!!! This doesn't look right.
class Generator(Function):
def __init__(self, name, argnames, defaults, flags, doc, code):
# self.decorators = decorators
self.name = "\'" + str(name) + "\'"
self.argnames = argnames
self.defaults = defaults
self.flags = flags
self.doc = doc
self.code = code
def __repr__(self):
return "Function(%s, %s, %s, %s, %s, %s)" % \
(self.name, self.argnames,\
self.defaults, self.flags, self.doc, self.code)
def convertFunction(node):
return Generator(node.name,
node.argnames, node.defaults, node.flags,
node.doc, node.code)
if __name__=="__main__":
## this stuff is all test code
## so by convention we put it in one of these blocks
t = Transformer()
t.on(Discard, expressListComp)
t.on(ListComp, expressListComp)
t.on(Function, convertFunction)
#newTree = t.apply(tree)
#print t.apply(tree)
#tree.filename = ""
#gen = pycodegen.ModuleCodeGenerator(tree)
#code = gen.getCode()
#exec code
| No admin address has been configured | ViewVC Help |
| Powered by ViewVC 1.0.5 |