La partie obligatoire de ce TP sera notée par votre intervenant pendant la séance de TP. Vous devrez donc appeler votre intervenant à chaque fois que vous avez terminé une question.
Les questions « bonus » peuvent être envoyée par email à votre intervenant pendant la semaine (7 jours) qui suivent votre séance de TP. N'oubliez pas de mettre votre nom ainsi que votre filière en commentaire dans les fichiers que vous nous envoyez...
Attention : pour que les questions bonus soient prises en compte, il faut que les questions obligatoires aient été traitées. Si vous n'avez pas fini les questions obligatoires en TP, il faut donc les finir chez vous avant de traiter les questions bonus...
La note ne valide pas seulement le résultat de votre programme, mais également son style :
y = x * 2 # y est le double de x
n'apporte rien),
Vérifiez ces points avant de demander à votre intervenant de valider votre code.
D'autre part, vous aurez besoins des fichiers suivant pour ce TP :
Le but de ce TP est de revoir certains concepts vu au premier semestre (boucles, conditionnelles, fonctions) en insistant sur la qualité du code écrit. Pour ceci, il faudra suivre les règles vues en cours concernant :
#
de Python),
Dans la première partie, nous allons modéliser (et dessiner) la trajectoire d'un boulet de canon en fonction de l'angle de tir, de la vitesse initiale du boulet et de sa masse. Nous chercherons ensuite à ajuster automatiquement l'angle de tir pour essayer d'atteindre une cible précise.
Dans la seconde partie, nous utiliserons une méthode itérative pour calculer les zéros d'un polynôme dans les nombres complexes. Le comportement de cette méthode sur les points du plan permettra de dessiner des fractales bien connues des mathématiciens.
partie 1 | partie 2 |
La trajectoire d'un objet inerte est régie par les lois de la mécanique. Nous allons utiliser une approximation de ces lois pour modéliser de manière discrète la trajectoire d'un boulet de canon.
À un instant t donné, le boulet a
et il est soumis à la force d'attraction terrestre. Au temps t + ε, la position du boulet ainsi que sa vitesse seront modifiées en utilisant les formules
Pour que la modélisation ressemble à la réalité physique, il faut que ε soit assez petit.
Écrivez une fonction "trajectoire_boulet
" qui prend en argument les valeurs suivantes :
angle
: l'angle du canon, en degrés, par rapport à l'horizontal
masse
: la masse, en kilogramme, du boulet de canon (5kg est une valeur pertinente)
vitesse
: la vitesse, en mètre/s, du boulet à la sortie du canon (125 m/s est une valeur pertinente).
dt
: la valeur ε, en centièmes de secondes. Si cette valeur n'est pas fournie, votre fonction utilisera la valeur 1
par défaut.
freq
: la fréquence des affichages. En effet, si l'on dessine le boulet trop souvent, on ne pourra pas voir les positions successive du boulet. Une valeur de se paramètre de 50 n'affichera donc qu'une position sur 50. Si cette valeur n'est pas donnée, votre fonction utilisera la valeur 10
par défaut.
Votre fonction devra calculer toutes les valeurs successive du boulet jusqu'à ce qu'il atteigne le sol. Elle affichera (en utilisant la fonction dessine_boulet(x,y)
) le boulet à la fréquence demandée.
from math import sin,cos,pi
"Run" -> "Run Module F5"
) et d'utiliser la petite interface.
Nous cherchons maintenant à atteindre une cible, avec une précision de 1 mètre. Pour ceci, il faudra tirer des boulets (avec la fonction trajectoire_boulet
) et modifier l'angle en fonction de la distance parcourue par le boulet :
Le principe général d'une recherche dichotomique est de diviser son espace de recherche par deux à chaque étape. Au début, on sait simplement que l'angle cherché est entre 45° et 0° ; ensuite, qu'il est entre (par exemple) 45° et 22.5° ; ensuite, qu'il est entre (par exemple) 33.75° et 22.5°, etc.
Écrivez la fonction dichotomie
, qui prend en argument :
cible
: la distance entre le canon et la cible, en mètres,
masse
, vitesse
, dt
et freq
avec la même interprétation que dans la question précédente.
Votre fonction appellera la fonction précédente trajectoire
pour calculer et afficher les trajectoires du boulet.
Vous pouvez essayer de tirer « en cloche » en choisissant des angles entre 45° et 90°, ou « ras le sol » en choisissant des angles entre 0° et 45°.
La méthode de Newton est une méthode pour calculer des approximations de plus en plus précises de solutions d'équations de la forme f(z) = 0, où f est une « bonne fonction ». Nous allons nous intéresser au cas où f est un polynôme, et dans un premier temps, au cas où f(z) = z3 + 1.
La méthode de Newton fonctionne de la manière suivante : sous les bonnes hypothèses,
On peut ainsi calculer des approximations x2, ..., xn de plus en plus précises. Vous pouvez consulter la page Wikipedia sur la méthode de Newton pour plus de détails.
Pour cette partie, vous aurez besoin du fichier à trous suivant : frac-poly.py.
Python possède un type spécial pour les nombres complexes :
Python 3.1.3 (r313:86834, Nov 28 2010, 10:01:07) [GCC 4.4.5] on linux2 Type "help", "copyright", "credits" or "license" for more information. >>> z = complex(1,2) (1+2j) >>> type(z) <class 'complex'> >>> z*z (-3+4j) >>> print("La partie réelle de z est", z.real, "et sa partie imaginaire est", z.imag) La partie réelle de z est 1.0 et sa partie imaginaire est 2.0
Les points importants sont :
z = complex(partie_réelle, partie_imaginaire)
+
, *
, /
, ...
z
avec z.real
, et à sa partie imaginaire avec z.imag
.
j
au lieu de la lettre i habituellement utilisée par les mathématiciens.
Écrivez une (mini) fonction module
qui calcule le module d'un nombre complexe.
Un polynôme est donné par le tableau de ses coefficients. Un polynôme est donc simplement un tableau de nombres complexes, où la case d'indice 0 est le terme constant, et la dernière case est le coefficient du monôme de plus haut degré...
Par exemple, le polynôme z3 + i = i + 0 z + 0 z2 + 1 z3 est représenté par [complex(0,1) , complex(0,0) , complex(0,0) , complex(1,0) ]
.
Écrivez une fonction degre
qui renvoie le degré d'un polynôme. La fonction prend un seul argument : P
, un polynôme complexe.
Écrivez une fonction evaluePolynome
qui calcule la valeur d'un polynôme en un point complexe. Elle prend deux arguments :
P
, un polynôme complexe,
z
, un nombre complexe.
Écrivez une fonction derivePolynome
qui calcule le polynôme dérivé d'un autre polynôme. Cette fonction a un unique argument, un polynôme P
à dériver...
Nous avons maintenant tous les ingrédients pour pouvoir programmer la méthode de Newton. Vous devrez calculer des approximations de plus en plus précises, et vous arrêter quand l'une des deux conditions suivantes est satisfaite :
epsilon
prêt, une solution de l'équation f(zi) = 0
max_iterations
approximations.
Écrivez la fonction newton
qui prend 5 arguments :
P
un polynôme complexe,
dP
, le polynôme dérivé du précèdent,
z
, un nombre complexe représentant l'approximation initiale de la solution,
epsilon
, un nombre réel, petit, spécifiant la précision que l'on souhaite obtenir (1e-10
est une bonne valeur par défaut),
max_iterations
, le nombre maximal d'approximations que l'on calcule.
La fonction doit renvoyer une paire (i,z)
, où
i
est le nombre d'itérations faites, ou -1
si l'on a dépassé max_iterations
itérations,
z
est la dernière approximation calculée.