Calcul formel
Professeurs référents :
M FAURY (ISN)
Objectif initial :
Reconnaître une chaîne de caractères et la décomposer en fonctions en fonction des opérateurs présents dans l’expression et en fonction des différents nombres arguments de ces opérateurs, et ce afin de pouvoir simplifier une écriture de nombre.
Objectif final :
Dériver une expression mathématique.
Appliquer une formule à une expression.
Cahier des charges :
Utilisation du codage Python |
Parvenir à un code fonctionnant et dérivant donc par conséquent une expression mathématique |
Tâches à réaliser :
TALAZAC Mathias | MASSE Maxence |
Interpréter une chaîne de caractère et renvoyer un dictionnaire contenant pour chaque opérateurs une fonction et renvoyant chaque argument de chaque opérateur | Décoder un dictionnaire |
Résoudre l’équation présente dans le dictionnaire |
Fonction Interpreter (Mathias) :
print ("Entrez votre expression ci dessous :") chaine = input() """ L'utilisateur rentre l'expression mathématique selon la syntaxe suivante : 8+3*x et non pas 8+3x """ def Somme (a,b): return a+b def Difference (a,b) : return a-b def Produit (a,b): return a*b def Quotient (a,b): return a/b def Exposant (a,b): return a**b def interpreter(chaine): #Définition de la fonction """1ère étape Interprétation d'une expression mathématique à un opérateur sous forme de chaine de caractères Par exemple: "3600/2" >>> {'fct': <function Quotient at 0x000000000436D6A8>, 'arg': (3600.0, 2.0)} 2ème étape : Interprétation d'une expression mathématique à plusieurs opérateurs sous forme de chaine de caractères Par exemple: "3600+27/6*10+2-25" >>> {'fct': <function Somme at 0x000000000436D620>, 'arg': (3600.0, {'fct': <function Somme at 0x000000000436D620>, 'arg': ({'fct': <function Produit at 0x000000000436D510>, 'arg': ({'fct': <function Quotient at 0x0000000003E6E7B8>, 'arg': (27.0, 6.0)}, 10.0)}, {'fct': <function Difference at 0x000000000436D6A8>, 'arg': (2.0, 25.0)})})} 3ème étape : Ajout d'une variable dans l'expression Par exemple : "3600*x+27/6*10+2-25" >>>{'fct': <function Somme at 0x000000000431D510>, 'arg': ({'fct': <function Produit at 0x000000000431DB70>, 'arg': (3600.0, <built-in function vars>)}, {'fct': <function Somme at 0x000000000431D510>, 'arg': ({'fct': <function Produit at 0x000000000431DB70>, 'arg': ({'fct': <function Quotient at 0x000000000431D488>, 'arg': (27.0, 6.0)}, 10.0)}, {'fct': <function Difference at 0x000000000431D8C8>, 'arg': (2.0, 25.0)})})} """ dico={} for i,c in enumerate(chaine) : #On parcours la chaine et a chaque caractère on y associe un indice if c == "+" : #On cherche en premier les additions et les soustractions car elles sont les moins prioritaires. a=chaine[0:i] #On sépare en deux parties (a et b) la chaine de caractères de chaque côté de l'opérateur d'indice i b=chaine[i+1:] #On sépare en deux parties (a et b) la chaine de caractères de chaque côté de l'opérateur d'indice i dico['fct']=Somme #L'opérateur est un '+' on renvoie donc la fonction Somme dans le dictionnaire dico['arg']=(interpreter(a),interpreter(b)) #Et comme arguments de cette somme on interprète les chaines de caractères a et b return dico #On renvoie le tout dans un dictionnaire for i,c in enumerate(chaine) : #On parcours la chaine et a chaque caractère on y associe un indice if c == "-" : #On cherche en premier les additions et les soustractions car elles sont les moins prioritaires. a=chaine[0:i] #On sépare en deux parties (a et b) la chaine de caractères de chaque côté de l'opérateur d'indice i b=chaine[i+1:] #On sépare en deux parties (a et b) la chaine de caractères de chaque côté de l'opérateur d'indice i dico['fct']=Difference #L'opérateur est un '-' on renvoie donc la fonction Difference dans le dictionnaire dico['arg']=(interpreter(a),interpreter(b))#Et comme argument de cette différence on interprète les chaines de caractères a et b return dico #On renvoie le tout dans un dictionnaire for i,c in enumerate(chaine) : #On parcours la chaine et a chaque caractère on y associe un indice if c =="/": #On cherche ensuite les divisions car elles sont plus prioritaire que les additions et soustractions mais moins prioritaires que les multiplications et que les exposants a=chaine[0:i] #On sépare en deux parties (a et b) la chaine de caractères de chaque côté de l'opérateur d'indice i b=chaine[i+1:] #On sépare en deux parties (a et b) la chaine de caractères de chaque côté de l'opérateur d'indice i dico['fct']=Quotient #L'opérateur est un '/' on renvoie donc la fonction Quotient dans le dictionnaire dico['arg']=(interpreter(a),interpreter(b))#Et comme arguments de ce quotient on interprète les chaines de caractères a et b return dico #On renvoie le tout dans un dictionnaire for i,c in enumerate(chaine) : #On parcours la chaine et a chaque caractère on y associe un indice if c=="*": #On cherche ensuite les multiplications car elles sont plus prioritaire que les additions,les soustractions mais moins prioritaires que les exposants a=chaine[0:i] #On sépare en deux parties (a et b) la chaine de caractères de chaque côté de l'opérateur d'indice i b=chaine[i+1:] #On sépare en deux parties (a et b) la chaine de caractères de chaque côté de l'opérateur d'indice i dico['fct']=Produit #L'opérateur est un '*' on renvoie donc la fonction Produit dans le dictionnaire dico['arg']=(interpreter(a),interpreter(b))#Et comme arguments de ce produit on interprète les chaines de caractères a et b return dico #On renvoie le tout dans un dictionnaire for i,c in enumerate(chaine) : #On parcours la chaine et a chaque caractère on y associe un indice if c=="^": #On cherche enfin les exposants car ils sont le plus prioritaire de tous a=chaine[0:i] #On sépare en deux parties (a et b) la chaine de caractères de chaque côté de l'opérateur d'indice i b=chaine[i+1:] #On sépare en deux parties (a et b) la chaine de caractères de chaque côté de l'opérateur d'indice i dico['fct']=Exposant #L'opérateur est un '^' on renvoie donc la fonction Exposant dans le dictionnaire dico['arg']=(interpreter(a),interpreter(b))#Et comme arguments de cet exposant on interprète les chaines de caractères a et b return dico #On renvoie le tout dans un dictionnaire for i,c in enumerate(chaine): #On parcours la chaine et a chaque caractère on y associe un indice if c=='x': #On cherche enfin si il y a du 'x' dans l'expression return 'x' #Si il y en a on le renvoie comme argument dans le dictionnaire return float(chaine) #Si on ne trouve pas d'opérateur ni de 'x' c'est alors que l'argument est en nombre on transforme donc la chaine de caractères en un nombre décimal print(interpreter(chaine)) #On affiche le résultat et ça marche !
Fonction de résolution (Maxence) :
import sys sys.setrecursionlimit(10500) #Ces deux lignes servent à augmenter la taille de la pile de récursion et donc de supporter des expressions plus grandes from math import * #Cette ligne sert à importer tous les opérateurs mathématiques nécessaires def somme(a,b): if estUnNombre(a) : if estUnNombre(b) : return a+b else : return a+evaluer(b) else : if estUnNombre(b): return evaluer(a)+b else : return evaluer(a)+evaluer(b) #Ces lignes (qui sont les mêmes pour toutes les opérations) demandent si les arguments sont bien des nombres : elles les renvoient à la fonction évaluer si ce ne sont pas des nombres et résoud l'équation si les deux sont des nombres def difference(a,b): if estUnNombre(a) : if estUnNombre(b) : return a-b else : return a-evaluer(b) else : if estUnNombre(b): return evaluer(a)-b else : return evaluer(a)-evaluer(b) def produit(a,b): if estUnNombre(a) : if estUnNombre(b) : return a*b else : return a*evaluer(b) else : if estUnNombre(b): return evaluer(a)*b else : return evaluer(a)*evaluer(b) def quotient(a,b): if estUnNombre(a) : if estUnNombre(b) : return a/b else : return a/evaluer(b) else : if estUnNombre(b): return evaluer(a)/b else : return evaluer(a)/evaluer(b) def cosinus(a): if estUnNombre(a) : return cos(a) else : return cos(evaluer(a)) def sinus(a): if estUnNombre(a) : return sin(a) else : return sin(evaluer(a)) def exponentielle(a): if estUnNombre(a) : return exp(a) else : return exp(evaluer(a)) def racine(a): if estUnNombre(a) : return sqrt(a) else : return sqrt(evaluer(a)) def estUnNombre(x): if type(x)==float or type(x)==int or type(x)==complex: return True else: return False #Cette fonction vérifie si l'argument des opérations est, ou non, un nombre # 156.5+cos37/sqrt25 dico = {'fct':somme, 'arg':[156.5, {'arg':[{'arg':[37.0], 'fct':cosinus},{'arg':[25.0], 'fct':racine}], 'fct':quotient}]} #Le dictionnaire est organisé sous une forme : dico={-FONCTION-:[-ARGUMENT1-,-ARGUMENT2-]} def evaluer(dico): return dico['fct'](*dico['arg']) print(evaluer(dico)) #Cette fonction décompose le dictionnaire en une multitude de petites équations que les fonctions somme, différence... peuvent résoudre
Fichiers du projet
- Ajouter un(des) fichier(s) puis cliquer sur Téléverser.
- Rafraichir la page pour vérifier que le dépôt a bien eu lieu.