Ce script fait partie des projets Python de HyperSkill.
j'ai fait toute la formation python de Hyperskill pendant le Confinement 2020.
| # write your code here | |
| from string import ascii_letters, digits | |
| class Calculator: | |
| def __init__(self): | |
| self.variables = {} | |
| while True: | |
| self.user_input = input() | |
| if self.user_input.startswith("/"): | |
| msg = self.command() | |
| elif self.user_input == "": | |
| continue | |
| elif self.user_input[0] in ascii_letters: | |
| msg = self.process() | |
| elif self.user_input[0] not in ascii_letters + digits: | |
| msg = "Invalid expression" | |
| else: | |
| msg = self.calculate | |
| if msg or msg == 0: | |
| print(msg) | |
| def command(self): | |
| if self.user_input == "/exit": | |
| print("Bye!") | |
| exit(0) | |
| elif self.user_input == "/help": | |
| return "This program adds or subtracts numbers." | |
| else: | |
| return f"Unknown command" | |
| @staticmethod | |
| def add(a, b): | |
| return int(a) + int(b) | |
| @staticmethod | |
| def sub(a, b): | |
| return int(a) - int(b) | |
| def split(self): | |
| raw_splitted = list(self.user_input) | |
| operators = ("+", "-") | |
| buffer = [] | |
| splitted = [] | |
| for i in raw_splitted: | |
| if i in operators and len(splitted) == 0: | |
| buffer.append(i) | |
| if i not in operators and len(splitted) == 0: | |
| splitted.append(i) | |
| elif i not in operators and len(buffer) == 1: | |
| pos = buffer.pop() | |
| splitted.append(f"{pos}{i}") | |
| elif not i.isdigit() and not splitted[-1][-1].isdigit(): | |
| splitted[-1] += i | |
| elif i.isdigit() and splitted[-1][-1].isdigit(): | |
| splitted[-1] += i | |
| else: | |
| splitted.append(i) | |
| if len(splitted) == 1: | |
| if splitted[0] == "-" and splitted[1].isdigit(): | |
| return "".join(splitted), False | |
| elif splitted[0] == "+" and splitted[1].isdigit(): | |
| return splitted[1], True | |
| elif len(splitted) == 1 and splitted[0][1:].isdigit(): | |
| return splitted[0], True | |
| elif len(splitted) == 1 and splitted[0].isdigit(): | |
| return splitted[0], True | |
| return "Invalid expression", True | |
| return splitted, False | |
| @property | |
| def calculate(self): | |
| calc_list, status = self.split() | |
| if status: | |
| return calc_list | |
| if status: | |
| return calc_list[0] | |
| if len(calc_list) < 2: | |
| return "Invalid expression" | |
| calc_list.reverse() | |
| result_list = [] | |
| try: | |
| a, method, b = (calc_list.pop() for _ in range(3)) | |
| except IndexError: | |
| return "Invalid expression" | |
| if "+" in set(method): | |
| result_list.append(self.add(a, b)) | |
| elif "-" in set(method): | |
| if len(method) % 2 == 0: | |
| result_list.append(self.add(a, b)) | |
| else: | |
| result_list.append(self.sub(a, b)) | |
| while len(calc_list) > 0: | |
| a = result_list.pop() | |
| method, b = (calc_list.pop() for _ in range(2)) | |
| if "+" in set(method): | |
| result_list.append(self.add(a, b)) | |
| elif "-" in set(method): | |
| if len(method) % 2 == 0: | |
| result_list.append(self.add(a, b)) | |
| else: | |
| result_list.append(self.sub(a, b)) | |
| return result_list[0] | |
| def process(self): | |
| self.user_input = self.user_input.replace(" ", "") | |
| if "=" in self.user_input: | |
| return self.process_variable() | |
| else: | |
| if len(self.user_input.split()) == 1 and not any(elem in list(self.user_input) for elem in ["+", "-"]): | |
| if self.user_input in self.variables.keys(): | |
| return self.print_variable() | |
| else: | |
| return "Unknown variable" | |
| else: | |
| return self.calculate_var() | |
| def process_variable(self): | |
| try: | |
| var, value = self.user_input.split("=") | |
| except ValueError: | |
| return "Invalid assignment" | |
| if not all(elem in list(ascii_letters) for elem in list(var)): | |
| return "Invalid identifier" | |
| else: | |
| if self.is_digit(value): | |
| self.variables[var] = value | |
| elif not all(elem in list(ascii_letters) for elem in list(value)): | |
| return "Invalid assignment" | |
| else: | |
| if value not in self.variables.keys(): | |
| return "Unknown variable" | |
| else: | |
| self.variables[var] = self.variables[value] | |
| return | |
| def print_variable(self): | |
| return self.variables[self.user_input] | |
| def calculate_var(self): | |
| calc_list = self.split_var() | |
| variables = [elem for elem in set(calc_list) if elem in ascii_letters] | |
| if not all(elem in self.variables.keys() for elem in variables): | |
| return "Unknown variable" | |
| for elem in range(len(calc_list)): | |
| if calc_list[elem] in self.variables: | |
| calc_list[elem] = self.variables[calc_list[elem]] | |
| self.user_input = "".join(calc_list) | |
| return self.calculate | |
| def split_var(self): | |
| raw_splitted = list(self.user_input) | |
| operators = ("+", "-") | |
| buffer = [] | |
| splitted = [] | |
| for i in raw_splitted: | |
| if i in operators and len(splitted) == 0: | |
| buffer.append(i) | |
| elif i in operators and all(elem not in list(ascii_letters+digits) for elem in list(splitted[-1][-1])): | |
| splitted[-1] += i | |
| elif i not in operators and len(buffer) == 1: | |
| pos = buffer.pop() | |
| splitted.append(f"{pos}{i}") | |
| else: | |
| splitted.append(i) | |
| return splitted | |
| @staticmethod | |
| def is_digit(value): | |
| try: | |
| int(value) | |
| return True | |
| except ValueError: | |
| return False | |
| Calculator() |
cyvax - 2025