def handle_zeros_for_point(self, point): """ Checks if the function can be parsed, and if it can't, it sends the point to be fixed """ try: FunctionParser.parse(point['formula']) except InvalidTokenException as e: # function cannot be parsed self.fix_zeros_for_point(point, e.position)
def handle_parameters_for_point(self, point): """ If the equation is valid, it will pass the point and the expression tree to get fixed """ try: expression_tree = FunctionParser.parse(point['formula']) if len(expression_tree['identifier_names']) > 0: self.fix_parameters_for_point(point, expression_tree['identifier_names']) except: print point['id']
def __init__(self): self.parser = Parser() self.operators = self.parser.get_operators() self.functions = { '+': lambda a, b: a + b, '-': lambda a, b: a - b, '*': lambda a, b: a * b, '^': math.pow, '/': lambda a, b: a / b, '%': lambda a, b: a % b, '<': lambda a, b: a < b, '>': lambda a, b: a > b, '==': lambda a, b: a == b, '!=': lambda a, b: a != b, '<=': lambda a, b: a <= b, '>=': lambda a, b: a >= b, '!': math.factorial, 'sum': lambda *elements: sum(elements), 'abs': lambda number: abs(number), 'sin': math.sin, 'asin': math.asin, 'asinh': math.asinh, 'cos': math.cos, 'acos': math.acos, 'acosh': math.acosh, 'tg': math.tan, 'atg': math.atan, 'atgh': math.atanh, 'max': max, 'min': min, 'ln': math.log, 'log': math.log, 'log10': math.log10, } self.parser.functions = self.get_functions() self.symbols = { 'pi': math.pi, 'e': math.e, 'inf': math.inf, 'nan': math.nan, 'tau': math.tau, } self.equations = [] self.end_function = None self.epsilon = None self.number_of_threads = None self.maximize = True self.multi_threading = True self.radian = None self.centre = None self.initialize()
def parse_formula(formula): try: expression_tree = FunctionParser.parse(formula["formula"]) return jsonify( { "identifier_names": expression_tree["identifier_names"], "function_names": expression_tree["function_names"], "variable_names": expression_tree["variable_names"], } ) except Exception as e: js = json.dumps(e.__dict__) response = Response(js, status=400, mimetype="application/json") return response
def execute(self, command): command = command.split(' ', 1) args = [] if len(command) is 2: command[1] = Parser.remove_spaces(command[1]) args.extend(command[1].split('|')) command = command[0] result = None try: result = self.commands[command](*args) except KeyError: print(self.unknown_command(command)) except TypeError as e: print(command + ": " + str(e)) if result is not None: print(str(result))
from function_parser.FunctionParser import * ex = 'sin(0.2.*x)' parser = FunctionParser(ex) f = parser.getFunction() print(f(2))
class Executor: def __init__(self): self.parser = Parser() self.operators = self.parser.get_operators() self.functions = { '+': lambda a, b: a + b, '-': lambda a, b: a - b, '*': lambda a, b: a * b, '^': math.pow, '/': lambda a, b: a / b, '%': lambda a, b: a % b, '<': lambda a, b: a < b, '>': lambda a, b: a > b, '==': lambda a, b: a == b, '!=': lambda a, b: a != b, '<=': lambda a, b: a <= b, '>=': lambda a, b: a >= b, '!': math.factorial, 'sum': lambda *elements: sum(elements), 'abs': lambda number: abs(number), 'sin': math.sin, 'asin': math.asin, 'asinh': math.asinh, 'cos': math.cos, 'acos': math.acos, 'acosh': math.acosh, 'tg': math.tan, 'atg': math.atan, 'atgh': math.atanh, 'max': max, 'min': min, 'ln': math.log, 'log': math.log, 'log10': math.log10, } self.parser.functions = self.get_functions() self.symbols = { 'pi': math.pi, 'e': math.e, 'inf': math.inf, 'nan': math.nan, 'tau': math.tau, } self.equations = [] self.end_function = None self.epsilon = None self.number_of_threads = None self.maximize = True self.multi_threading = True self.radian = None self.centre = None self.initialize() def initialize(self): self.end_function = None self.epsilon = 0.1**6 self.number_of_threads = 10 self.maximize = True self.multi_threading = True self.radian = 1000.0 self.centre = 0.0 def add(self, equation): u"""Adds "subject to" function""" self.equations.append(equation) def set_radian(self, radian): self.radian = radian def remove(self, index): try: del self.equations[int(index)] except TypeError: print("Index out of range") def set_epsilon(self, eps): self.epsilon = float(eps) def set_end_function(self, equation): self.end_function = equation # TODO finish def create_custom_function(self, name, body): if type(body) is str: body = self.parser.parse(body) function_name = name exec("def " + function_name + "(*args):\n\tvar = self.get_decisibody ") self.functions[function_name] = name def clear(self): self.equations.clear() def clear_all(self): self.clear() self.initialize() def get_operators(self): return self.functions.keys() def get_functions(self): return [ key for key, func in self.functions.items() if key not in self.operators ] def set_number_of_threads(self, size): self.number_of_threads = size def set_range(self, begging, end): self.radian = abs(end - begging) / 2 self.centre = (end - begging) def get_decision_variables(self, expression=None): if expression is None: expression = self.end_function if type(expression) is str: expression = self.parser.parse(expression) excluded = list(self.get_operators()) + list(self.symbols.keys()) def find_operators(tmp_expression): tmp = set() for item in tmp_expression: if type(item) is list: tmp.update(find_operators(item)) elif item not in excluded and type(item) is str: tmp.add(item) return tmp return find_operators(expression) @staticmethod def fill_variables(equation, values): """ :param equation: list representing equation :param values: map, where keys are variables like x or y and values are floats """ return forEach(equation, lambda x: values[x], lambda x: x in values) def calculate(self, equation): if type(equation) is str: result = self.parser.parse(equation) else: result = equation[:] # FIXME: it can be better if type(result[1]) is list: if len(result[1]) > 0: try: if type(result[1][0]) is list: result[1][0] = self.calculate(result[1][0]) except TypeError: pass if type(result[1]) is list: if len(result[1]) is 2: try: if type(result[1][1]) is list: result[1][1] = self.calculate(result[1][1]) except TypeError: pass return self.functions[result[0]](*result[1]) def execute(self): # initialize radian = self.radian # parse string equations to list representations equations = forEach(self.equations, lambda item: self.parser.parse(item), recursion=False) end_function = self.parser.parse(self.end_function) # change constant symbols to matching floats equations = self.fill_variables(equations, self.symbols) variables = self.get_decision_variables() initial_point = {key: self.centre for key in variables} fields = self.ExecuteFields( initial_point, self.calculate(self.fill_variables(end_function, initial_point))) lock = Lock() if self.multi_threading: queue = Queue() def threads_task(): while True: item = queue.get() if item is None: break item() queue.task_done() threads = [] for i in range(self.number_of_threads): t = Thread(target=threads_task) t.daemon = True threads.append(t) t.start() def number_of_samples(): return int((radian + 10)**len(variables)) def random_values(): """:return point inside figure, where best_solution is center""" return { key: uniform(fields.best_point[key] - radian, fields.best_point[key] + radian) for key in variables } def find_possible_result(): point = random_values() if all([ self.calculate(self.fill_variables(equation, point)) for equation in equations ]): tmp_result = self.calculate( self.fill_variables(end_function, point)) with lock: if self.maximize: is_positive_difference = tmp_result > fields.best_result else: is_positive_difference = tmp_result < fields.best_result if is_positive_difference: fields.best_point = point fields.best_result = tmp_result # end of initialization while radian - self.epsilon > 0: for index in range(number_of_samples()): if self.multi_threading: queue.put(find_possible_result) else: find_possible_result() if self.multi_threading: queue.join() print(radian, ":", fields.best_point, " - times:", number_of_samples()) radian *= 0.925 return fields.best_point class ExecuteFields: def __init__(self, point, result): self.best_point = point self.best_result = result self.task_index = 0
def load_calculations(self): wb = xlrd.open_workbook(self.file_path) sheet = wb.sheet_by_name("Calculations ID Table") self.calculations = dict() current_calculation = { "id": None, "code": None, "description": None, "formula": None, "parameters": set(), "units": None } for row_num in range(3, sheet.nrows + 1): if row_num < sheet.nrows: id = sheet.cell(row_num, 1).value code = sheet.cell(row_num, 2).value description = sheet.cell(row_num, 3).value formula = sheet.cell(row_num, 4).value energy_point_code = sheet.cell(row_num, 6).value numeric_point_code = sheet.cell(row_num, 8).value calculated_point_code = sheet.cell(row_num, 10).value units = sheet.cell(row_num, 12).value else: code = None if (code or row_num == sheet.nrows) and (current_calculation["code"] is None or code != current_calculation["code"]): if current_calculation["code"]: expression_tree = None try: expression_tree = FunctionParser.parse(current_calculation["formula"]) identifier_names = set(expression_tree["identifier_names"]) if len(current_calculation["parameters"] - identifier_names) > 0: logging.info("Unknown parameters in formula for calculation " + current_calculation["code"]) current_calculation["parameters"] = identifier_names self.calculations[current_calculation["id"]] = current_calculation except Exception as e: logging.error("Error parsing formula for calculation " + current_calculation["code"]) current_calculation = { "id": id, "code": code, "description": description, "formula": formula.split("=")[1], "parameters": set(), "units": units } if energy_point_code: current_calculation["parameters"].add(energy_point_code.upper()) if numeric_point_code: current_calculation["parameters"].add(numeric_point_code.upper()) if calculated_point_code: current_calculation["parameters"].add(calculated_point_code.upper()) logging.info("Found " + str(len(self.calculations)) + " calculations")
None) while object_builder.stop_build(ar_node) is False: top_trio = object_builder.search_top(ar_node) print(top_trio) lec = top_trio.lec top_index = self.infl_point(lec) if isinstance(lec[top_index], object_types.Function) or isinstance( top_element, object_types.UnaryMinus): left_lec = None right_lec = lec[1:] else: left_lec = lec[0:top_index] right_lec = lec[top_index + 1:] duo = self.build_ar_node(None, left_lec, right_lec, None, top_trio) ar_node = ar_node + duo for node in ar_node: if node: if node.parent is None: result = node.calc() print(f'result{result}') return result if __name__ == '__main__': obj = FunctionParser(['math']) builder = TreeBuilder() string1 = '5*(3+3*(5*5))' arr_node = builder.build_tree(string1) print(f'result {arr_node}')