def evaluate(self, env, **rest): if len(self.children) == 0: return getNil() if self.children[0].getType() == OPENING_PARENTHESIS: firstChild = self.children[0].evaluate(env, **rest) else: firstChild = self.children[0] if firstChild.getType() == SYMBOL: if firstChild.value in self.operatorsDict: return self.operatorsDict[firstChild.value].evaluate( self.children[1:], env, **rest) else: fun = env.getFunction(firstChild.value) if fun: return self.callObject(fun, self.children[1:], env, **rest) else: raise BadInputException("The function " + firstChild.value + " is undefined") elif firstChild.getType() == FUN_OBJ: return self.callObject(firstChild, self.children[1:], env, **rest) else: print str(self.children[0].value) + ";;;;" raise BadInputException( "The first element of list should be a symbol\n")
def evaluate(self, params, env, **rest): if checkNumberOfParams(1, len(params), "hash"): tmp = params[0].evaluate(env) if tmp.getType() != SYMBOL: raise BadInputException( "first parameter of # should evaluate to function name") fn = env.getFunction(tmp.value) if not (fn): raise BadInputException( "first parameter of # should evaluate to function name") return fn.evaluate(env)
def evaluate(self, params, env, fnName="#<FUNCTION LAMBDA>"): if checkNumberOfParams(2, len(params), "lambda"): if params[0].getType() != LIST: raise BadInputException("missing lambda list") argNames = [] for argName in params[0].children: if argName.getType() != SYMBOL: raise BadInputException( "each element of lambda list is expected to be a symbol" ) argNames.append(argName.value) return lisp_forms.Function(argNames, params[1], env, fnName)
def evaluate(self, params, env, **rest): if checkNumberOfParams(1, len(params), "comma"): if "calledByBackquote" in rest: raise BadInputException( "comma must occurs inside backquote block") return params[0].evaluate(env)
def checkNumberOfParams(expected, actual, operatorName): if expected != actual: raise BadInputException("Special operator " + operatorName + " expects " + str(expected) + " arguments (got " + str(actual) + " arguments") return True
def evaluate(self, params, env, **rest): if len(params) % 2 == 1: raise BadInputException("Invalid number of arguments for setq") key = None while len(params) > 0: key = params.pop(0) if key.getType() != SYMBOL: raise BadInputException("Variable name " + key.value + " is not a symbol") env.setLexicalVariable(key.value, params.pop(0).evaluate(env)) if key: return env.getVariable(key.value) else: return intr.getNil()
def evaluate(self, params, env): if checkNumberOfParams(3, len(params), "defun"): if params[0].getType() != SYMBOL: raise BadInputException( "first element of defun is expected to be a symbol") env.globalEnv.funDict[params[0].value] = Lambda().evaluate( params[1:], env, "#<FUNCTION " + params[0].value + ">" ) # making copy is undesirable because defun change the global environment return lisp_forms.Symbol(params[0].value)
def evaluate(self, params, env, **rest): if checkNumberOfParams(2, len(params), "cons"): res = params[1].evaluate(env) if res.isNil(): res = getEmptyList() if res.getType() != LIST: raise BadInputException( "second parameter of cons is expected to be a list") res.children.insert(0, params[0].evaluate(env)) return res
def evaluate(self, params, env, **rest): if checkNumberOfParams(3, len(params), "defmacro"): if params[0].getType() != SYMBOL: raise BadInputException( "first element of defun is expected to be a symbol") if params[1].getType() != LIST: raise BadInputException("missing lambda list") argNames = [] for argName in params[1].children: if argName.getType() != SYMBOL: raise BadInputException( "each element of lambda list is expected to be a symbol" ) argNames.append(argName.value) env.globalEnv.funDict[params[0].value] = lisp_forms.Macro( argNames, params[2], env, params[0].value ) # making copy is undesirable because defmacro change the global environment return lisp_forms.Symbol(params[0].value)
def funcall(self, params): env = self.env.getCopy() if self.restPresent: if len(params) < len(self.argNames) - 1: raise BadInputException("invalid number of arguments: " + str(len(params))) variables = dict( zip(self.argNames[0:len(self.argNames) - 1], params[0:len(self.argNames) - 1])) variables[self.argNames[len(self.argNames) - 1]] = List() variables[self.argNames[len(self.argNames) - 1]].children = params[len(self.argNames) - 1:] else: if len(params) != len(self.argNames): raise BadInputException("invalid number of arguments: " + str(len(params))) variables = dict(zip(self.argNames, params)) env.overwriteLexicalVariables(variables) res = self.body.evaluate(env) return res
def evaluate(self, params, env, **rest): if len(params) < 1: raise BadInputException("funcall expects at least one parameter") if params[0].getType() != SYMBOL: fn = params[0].evaluate(env) if fn.getType() != FUN_OBJ: raise BadInputException( "first parameter of funcall should evaluate to function") else: fn = env.getVariable(params[0].value) if not (fn): fn = env.getFunction(params[0].value) if not (fn): raise BadInputException("cannot find function " + params[0].value) args = [] for param in params[1:]: args.append(param.evaluate(env)) return fn.funcall(args)
def __init__(self, argNames, body, env, name): #searching for &rest self.restPresent = False for i in xrange(len(argNames)): if argNames[i] == "&rest": if i == len(argNames) - 2: self.restPresent = True break elif i < len(argNames) - 2: raise BadInputException( "too many variables are following &rest") else: raise BadInputException("&rest with no rest variable") self.argNames = argNames if self.restPresent: self.argNames[len(self.argNames) - 2] = self.argNames[len(self.argNames) - 1] self.argNames.pop() # it cannot be done in one line self.body = body self.env = env.getCopy() super(Function, self).__init__(name)
def evaluate(self, params, env, **rest): if checkNumberOfParams(1, len(params), "car"): res = params[0].evaluate(env) if res.isNil(): res = getEmptyList() if res.getType() != LIST: raise BadInputException("The value " + str(res.value) + " is not a list") if len(res.children) == 0: return getNil() return res.children[0]
def evaluate(self, params, env, **rest): if checkNumberOfParams(1, len(params), "cdr"): res = params[0].evaluate(env) if res.getType() != LIST: raise BadInputException("The value " + str(res.value) + " is not a list") if len(res.children) < 2: return getNil() form = lisp_forms.List() form.children = res.children[1:] return form
def evaluate(self, params, env, **rest): if len(params) == 2 or len(params) == 3: res = params[0].evaluate(env) if res.getType() == SYMBOL and res.value == "NIL": if len(params) == 3: return params[2].evaluate(env) else: return getEmptyList() else: return params[1].evaluate(env) else: raise BadInputException( "Special operator 'if' expects 2 or 3 arguments (got " + str(len(params)) + " arguments)")
def evaluate(self, params, env, **rest): if len(params) < 1: raise BadInputException("let expects at least one argument (got " + str(len(params)) + " arguments)") newVariables = {} for initExpr in params[0].children: if len(initExpr.children) > 0: varName = initExpr.children[0] value = initExpr.children[1].evaluate(env) else: varName = initExpr value = getNil() if varName.getType() != SYMBOL: raise BadInputException("Variable name " + str(varName.value) + " is not a symbol") newVariables[varName.value] = value newEnv = env.getCopy() newEnv.overwriteLexicalVariables(newVariables) res = getNil() for param in params[1:]: res = param.evaluate(newEnv) return res
def evaluate(self, env, **rest): val = env.getVariable(self.value) if val: return val raise BadInputException("The variable " + self.value + " is unbound")