def visitCons(self, elem): return C.Cons()
def visitHead(self, elem): return C.Head()
def visitLambda(self, elem): s = elem.head.s return C.Lambda(elem.head, self(elem.body))
def visitNil(self, elem): return C.Nil()
def visitString(self, elem): return C.String(elem.s)
def visitLambda(self, elem): return C.Lambda(self(elem.head), self(elem.body))
def visitSeq(self, elem): return C.Seq()
def visitInteger(self, elem): return C.Number(elem.n)
def visitTRUE(self, elem): return C.TRUE()
def visitIf(self, elem): return C.If()
def visitFALSE(self, elem): return C.FALSE()
def visitBottom(self, elem): return C.Bottom()
def visitApply(self, elem): self_copy = copy.deepcopy(self) return C.Apply(self_copy(elem.left), self_copy(elem.right))
def visitTail(self, elem): return C.Tail()
def visitAdd(self, elem): return C.Add()
def visitLet(self, elem): # return self(T.Apply(T.Lambda(elem.var, elem.expr), elem.val)) # return self(T.Apply(T.Lambda(elem.var, elem.expr), T.Apply(Y, T.Lambda(elem.var, elem.val)))) return C.Letrec([self(x) for x in elem.vars], [self(x) for x in elem.vals], self(elem.expr))
def visitMult(self, elem): return C.Mult()
def visitFloat(self, elem): return C.Number(elem.n)
def visitEqual(self, elem): return C.Equal()
def visitApply(self, elem): return C.Apply(self(elem.left), self(elem.right))
def visitSub(self, elem): return C.Sub()
def visitVariable(self, elem): if elem.s == "_|_": return C.Bottom() elif elem.s == "*": return C.Mult() elif elem.s == '+': return C.Add() elif elem.s == "-": return C.Sub() elif elem.s == "if": return C.If() elif elem.s == "==": return C.Equal() elif elem.s == "!=": return C.NEqual() elif elem.s == "head": return C.Head() elif elem.s == "tail": return C.Tail() elif elem.s == "seq": return C.Seq() elif elem.s == "Cons": return C.Cons() elif elem.s == "Nil": return C.Nil() elif elem.s == "null": return C.Null() elif elem.s == "True": return C.TRUE() elif elem.s == "False": return C.FALSE() elif elem.s == "concat": return C.Concat() return C.Variable(elem.s)
def visitVariable(self, elem): return C.Variable(elem.s)