def float_op(arguments, function, out_type, in_type): var = splitter(arguments[0]) var_data = get_symb(arguments[0]) if var_data["type"] != in_type: raise IncorrectOperandsError("Type: int, actual: {}".format(var_data["type"])) scope.insert_to_var(*var, function(var_data["value"]), out_type)
def operation(arguments, function, ctype="int", insert_type="int", ctype_list=False): """ Operation function. Used to provide some action for operations with 3 arguments, like: add, sub etc. :param arguments: arguments list :param function: function to execute with arguments :param ctype: type of arguments :param insert_type: type which be inserted into variable :param ctype_list: type can be one of the list. (ctype var is list) """ processed_args = [] for x in [1, 2]: data = get_symb(arguments[x]) if (not ctype_list and data["type"] != ctype) or (ctype_list and data["type"] not in ctype): raise IncorrectOperandsError("Type: {}, actual: {}".format(ctype, data["type"])) if insert_type == "int" or data["type"] == "int": processed_args.append(int(data["value"])) else: processed_args.append(data["value"]) arg1 = arguments[0]["__val__"].split("@") scope.insert_to_var(*arg1, function(*processed_args), insert_type)
def NOT(arguments, order): var = splitter(arguments[0]) data = get_symb(arguments[1]) value = {"true": "false", "false": "true"} if data["type"] != "bool": raise IncorrectOperandsError("Type: bool, actual: {}".format(data["type"])) scope.insert_to_var(*var, value[data["value"]], "bool")
def TYPE(arguments, order): var = splitter(arguments[0]) try: data = get_symb(arguments[1]) data = {"value": data["type"], "type": "string"} except MissingValueError: data = {"type": "string", "value": ""} scope.insert_to_var(var[0], var[1], value=data["value"], vtype="string")
def MOVE(arguments, order): """ Move symb to the variable """ arg1 = splitter(arguments[0]) arg2 = get_symb(arguments[1]) scope.insert_to_var(*arg1, arg2["value"], arg2["type"])
def POPS(arguments, order): """ POP DATA FROM STACK """ var = splitter(arguments[0]) stack = scope.STACK if len(stack) == 0: raise MissingValueError() data = stack.pop() scope.insert_to_var(*var, data["value"], data["type"])
def NOTS(arguments, order): var = splitter(arguments[0]) len_stack = len(scope.STACK) if len_stack < 1: raise VariableDoesntExist("actual len stack >= 1, len stack {}".format(len_stack)) data = scope.STACK[-1] if data["type"] != "bool": IncorrectOperandsError("Type: bool, actual: {}".format(data["type"])) bools = {"true": "false", "false": "true"} scope.insert_to_var(*var, bools[data["value"]], "bool")
def STRLEN(arguments, order): """ s = len(str) :param arguments: :return: """ var = splitter(arguments[0]) data = get_symb(arguments[1]) if data["type"] != "string": raise IncorrectOperandsError("Type: string, actual: {}".format(data["type"])) scope.insert_to_var(*var, len(data["value"]), "int")
def INT2CHARS(arguments, order): var = splitter(arguments[0]) len_stack = len(scope.STACK) if len_stack < 1: raise VariableDoesntExist("actual len stack >= 1, len stack {}".format(len_stack)) data = scope.STACK[-1] if data["type"] != 'int': raise IncorrectOperandsError("Type: int, actual: {}".format(data["type"])) try: data = chr(int(data["value"])) scope.insert_to_var(*var, data, "string") except (ValueError, OverflowError): raise StringError
def stack_function_cops(arguments, function): """ Wrapper to compare stack values """ var = splitter(arguments[0]) stack = scope.STACK[::] len_stack = len(stack) if len_stack < 2: raise VariableDoesntExist("actual len stack >= 2, len stack {}".format(len_stack)) if stack[-1]["type"] != stack[-2]["type"]: raise IncorrectOperandsError("Types in compare operands must be the same.") bools = {True: "true", False: "false"} scope.insert_to_var(*var, bools[function(stack[-1]["value"], stack[-2]["value"])], "bool")
def STRI2INTS(arguments, order): var = splitter(arguments[0]) len_stack = len(scope.STACK) if len_stack < 2: raise VariableDoesntExist("actual len stack >= 2, len stack {}".format(len_stack)) index = scope.STACK[-2] data = scope.STACK[-1] if data["type"] != "string": raise IncorrectOperandsError("Type: string, actual: {}".format(data["type"])) if index["type"] != "int": raise IncorrectOperandsError("Type: int, actual: {}".format(index["type"])) try: scope.insert_to_var(*var, ord(data[index]), "int") except Exception as e: print(e, file=sys.stderr) raise StringError
def stack_function(arguments, function, insert_type): """ Function that provides stack operations wrap :param arguments: arguments list :param function: function that will be executed :param insert_type: type ov data will be inserted :return: """ var = splitter(arguments[0]) stack = scope.STACK[::] len_stack = len(stack) if len_stack < 2: raise VariableDoesntExist("actual len stack 2, len stack {}".format(len_stack)) if stack[-1]["type"] != stack[-2]["type"]: raise IncorrectOperandsError("Types in compare operands must be the same.") scope.insert_to_var(*var, function(stack[-1]["value"], stack[-2]["value"]), insert_type)
def INT2CHAR(arguments, order): """ var - variable where data will be stored data - data that INT2CHAR will convert :param arguments: :return: """ var = splitter(arguments[0]) data = get_symb(arguments[1]) if data["type"] != 'int': raise IncorrectOperandsError("Type: int, actual: {}".format(data["type"])) try: data = chr(int(data["value"])) scope.insert_to_var(*var, data, "string") except (ValueError, OverflowError): raise StringError
def operation_arithmetic(arguments, function): symb1 = get_symb(arguments[1]) symb2 = get_symb(arguments[2]) if symb1["type"] != symb2["type"]: raise IncorrectOperandsError("Operands types are not the same: {} and {}".format(symb1["type"], symb2["type"])) if symb1["type"] == "int": rtype = "int" symb1 = int(symb1["value"]) symb2 = int(symb2["value"]) elif symb1["type"] == "float": rtype = "float" symb1 = float.fromhex(symb1["value"]) symb2 = float.fromhex(symb2["value"]) else: raise IncorrectOperandsError("Operand must be of type int or float. Actual: {} {}".format(symb1, symb2)) arg1 = arguments[0]["__val__"].split("@") scope.insert_to_var(*arg1, function(symb1, symb2), rtype)
def str_index(arguments, function, type): """ var - variable where data will be stored data - string index - index letter ord :param arguments: :return: """ var = splitter(arguments[0]) data = get_symb(arguments[1]) index = get_symb(arguments[2]) if data["type"] != "string": raise IncorrectOperandsError("Type: string, actual: {}".format(data["type"])) if index["type"] != "int": raise IncorrectOperandsError("Type: int, actual: {}".format(index["type"])) try: scope.insert_to_var(*var, function(data["value"][int(index["value"])]), type) except Exception as e: print(e, file=sys.stderr) raise StringError
def SETCHAR(arguments, order): var = splitter(arguments[0]) var_data = get_symb(arguments[0]) index = get_symb(arguments[1]) _string = get_symb(arguments[2]) if index["type"] != "int": raise IncorrectOperandsError("Type: int, actual: {}".format(index["type"])) if var_data["type"] != "string" or _string["type"] != "string": raise IncorrectOperandsError("Type of arg1 and arg3 must be str, actual: {}".format(index["type"])) try: var_data = list(var_data["value"]) var_data[int(index["value"])] = _string["value"][0] data = "".join(var_data) scope.insert_to_var(*var, data, "string") except IndexError: raise StringError("Index out of range") except: raise SemanthicError()
def READ(arguments, order): try: user_input = input() except EOFError: user_input = "" v_type = arguments[1]["__val__"] try: data = { "int": int, "string": str, "bool": lambda x: x.lower() if x.lower() == "true" else "false" }[v_type](user_input) except ValueError: if v_type == "int": data = 0 elif v_type == "string": data = "" else: raise InternalError("Something happend with type") var = splitter(arguments[0]) scope.insert_to_var(*var, data, v_type)