__author__ = 'RemiZOffAlex' __email__ = 'remizoffalex@mail.ru' class Engine: def __init__(self): self.__methods = {} self.debug = False self.stack = [] self.scopes = {'root': {}} self.scope = 'root' def register(self, name, handler): self.__methods[name] = handler def visit(self, node): method = node['kind'] visitor = self.__methods.get(method, self.__class__.generic_visit) result = visitor(self, node) return result def generic_visit(self, node): """Called if no explicit visitor function exists for a node.""" method = node['kind'] raise NotImplementedError('No visitor method {method} was defined for this expression: {node}'.format( method=method, node=node )) def variable_addition(self, name, value = None): current = self.scopes[self.scope] if name in current: raise Exception('Double declaration of the variable %s' % name) current[name] = value def variable_delete(self, name, value): current = self.scopes[self.scope] if name in current: del current[name] raise Exception('Переменная {} не найдена'.format(name)) def variable_exist(self, name): current = self.scopes[self.scope] return name in current def variable_get(self, name): scope = self.scopes[self.scope] if name in scope: result = scope[name] return result stack = [] if self.scope != 'root': stack.append(self.scope) while len(stack) > 0: scope_name = stack.pop() closures = list( filter( closure_include(scope_name), self.closures ) ) for closure in closures: stack.append(closure['parent']) scope = self.scopes[scope_name] if name in scope: result = scope[name] return result raise Exception('Переменная {} не найдена'.format(name)) def variable_set(self, name, value): current = self.scopes[self.scope] if name in current: current[name] = value return raise Exception('Переменная {} не найдена'.format(name)) def __getattr__(self, name): raise AttributeError('Вызван несуществующий метод {name}'.format(name=name)) def __getitem__(self, key): method = self.__methods[key] return method.function def __iter__(self): return iter(self.__methods) def __len__(self): return len(self.__methods) def __delitem__(self, key): del self.__methods[key] def __repr__(self): return repr(self.__methods)