{
 "cells": [
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "# Chapitre 6 : \"Modules et packages\"\n",
    "\n",
    "### <span class=\"bg-info\">« *(...) la méthode est bonne. C'est brutal, c'est maussade, mais c'est simple comme bonjour, inratable.* »</span>\n",
    "\n",
    "Georges Duhamel $-$ Chronique des Pasquier\n",
    "\n",
    "***"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "### <span class=\"bg-success\">CE QU'IL FAUT RETENIR</span>\n",
    "\n",
    "- Module : collection d’éléments de programme (fonctions, classes, données) apparentés réutilisables.\n",
    "- Modules et programme pricipal. Dès qu'une application est volumineuse ou complexe, la méthode Python est classiquement de la découper en modules. \n",
    "\n",
    "**Note : ** Quand un utilise un **notebook**, et seulement dans ce cas, on découpe l'application en **cellules**. Pour utiliser les fonctions définies dans des \"modules\", il est impératif de les éxécuter **avant** la cellule \"programme principale\". Dans le cas général, on sauvegarde les modules dans des fichiers textes, que l'on importe par l'instruction Python `import`.\n",
    "\n",
    "***"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "### exo06_01 ✓✓✓\n",
    "\n",
    "Dans le plan muni d'un repère orthonormé, les coordonnées sont nommées $x$ et $y$.\n",
    "\n",
    "Une courbe *C* est définie en polaire par l'expression de $r$ (distance par rapport à l'origine) en fonction de $\\theta$ (angle par rapport à l'axe des abscisses). Les coordonnées des points de la courbe sont alors :\n",
    "\n",
    "```text\n",
    "x = r(theta) * cos(theta)\n",
    "y = r(theta) * sin(theta)\n",
    "```\n",
    "\n",
    "On va *discrétiser* cette courbe en n'utilisant que quelques-uns de ses points, qui seront stokés dans une liste.\n",
    "\n",
    "Dans une cellule, écrire le module suivant :\n",
    "\n",
    "1. Définir une fonction `rTest()` qui reçoit l'argument $\\theta$ et qui retourne la fonction $|\\sin{\\theta}|$.\n",
    "2. Définir une fonction `listePoints()` qui reçoit 4 arguments : une fonction nommée `pol`, deux flottants `theta_ini` et `theta_fin`, un entier `nb_pas`. Cette fonction retourne une liste de points `(x, y)` obtenus en appelant la fonction `pol`, `theta` variant de `theta_ini` à `theta_fin` en `nb_pas` pas de même taille.\n",
    "3. Définir une fonction `dMax()` qui reçoit la liste produite par `listePoints()` et qui retourne le tuple `((x1, y1), (x2, y2))` des  coordonnées des deux points les plus éloignés l'un de l'autre sur cette courbe.\n",
    "4. Tester ce module à l'aide des appels suivants :\n",
    "\n",
    "```python\n",
    "points = listePoints(rTest, 0, pi/4, 4)\n",
    "x, y = dMax(points)\n",
    "print(\"Points les plus éloignés : ({:g}, {:g}) et ({:g}, {:g})\".format(*x, *y))\n",
    "```\n",
    "\n",
    "Dans une seconde cellule, écrire le programme principal.\n",
    "\n",
    "Déterminer les coordonnées des deux points les plus éloignés l'un de l'autre sur la courbe d'équation polaire : $$r = \\theta\\cdot\\sin{\\frac{\\theta}{2}}$$ où $\\theta$ varie de 0 à 2$\\pi$ en 180 pas."
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 2,
   "metadata": {
    "collapsed": true
   },
   "outputs": [],
   "source": [
    "# exo06_01 - module"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 2,
   "metadata": {
    "collapsed": true
   },
   "outputs": [],
   "source": [
    "# exo06_01 - programme principal"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "### exo06_02 ✓✓\n",
    "\n",
    "La fonction `creaPolyg(n)` définie ci-dessous reçoit un argument entier `n` et retourne une liste de `n` tuples à deux coordonnées qui sont des flottants compris entre `-10` et `+10` (bornes comprises). On interprète cette liste comme un polygone plan à `n` sommets.\n",
    "\n",
    "Recopier ce code dans une cellule et le compléter en définissant une fonction nommée `dmaxPolyg(pol)` qui reçoit un polygone et qui retourne la distance maximum entre deux sommets quelconques de ce polygone.\n",
    "\n",
    "```python\n",
    "from random import randint\n",
    "from math import hypot\n",
    "\n",
    "def creaPolyg(n) :\n",
    "    res = []\n",
    "    for i in range(n) :\n",
    "        res.append((randint(-10, 10), randint(-10, 10)))\n",
    "    return res\n",
    "```    \n",
    "\n",
    "Dans une seconde cellule, calculer :\n",
    "\n",
    "- La distance maximum entre deux sommets du polygone \n",
    "```python\n",
    "[(0.0 , 0.0) , (0.0 , 3.0) , (4.0 , 0.0)]\n",
    "```\n",
    "- La distance maximum entre deux sommets d’un polygone à `5` sommets nommé `p` et créé par la fonction `creaPolyg()`.\n",
    "\n",
    "**Rappel : ** La distance entre deux points $a$ et $b$ vaut $\\sqrt{(a_x - b_x)^2 + (a_y - b_y)^2}$"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 3,
   "metadata": {
    "collapsed": true
   },
   "outputs": [],
   "source": [
    "# exo06_02 - module"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 4,
   "metadata": {
    "collapsed": true
   },
   "outputs": [],
   "source": [
    "# exo06_02 - programme principal"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "### exo06_03 ✓✓\n",
    "\n",
    "La fonction `creaListe(n)` définie ci-dessous reçoit un argument entier `n` et retourne une liste de `n` flottants positifs ou nuls. On interprète cette liste comme la donnée des longueurs de `n` segments dans un plan.\n",
    "\n",
    "Recopier ce code dans une cellule et le compléter en définissant une fonction nommée `estTriangle(t)` qui reçoit une liste de trois flottants positifs et qui retourne le booléen **`True`** si ces longueurs peuvent être celles des côtés d’un triangle, **`False`** sinon (voir [exo02_04](../chapitre_02/chap02_exos.ipynb#exo02_04)).\n",
    "\n",
    "```python\n",
    "from random import randint\n",
    "\n",
    "def creaListe(n) :\n",
    "    res = []\n",
    "    for i in range(n) :\n",
    "        res.append(randint(0, 20) / 4)\n",
    "    return res\n",
    "```    \n",
    "\n",
    "Dans une seconde cellule, vérifier si les trois listes suivantes peuvent être les longueurs des côtés d’un triangle :\n",
    "\n",
    "```python\n",
    "[13, 4, 10]\n",
    "[13, 4, 1]\n",
    "L  # liste (de trois flottants) obtenue par un appel judicieux à la fonction creaListe()\n",
    "```"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 5,
   "metadata": {
    "collapsed": true
   },
   "outputs": [],
   "source": [
    "# exo05_03 - module"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 6,
   "metadata": {
    "collapsed": true
   },
   "outputs": [],
   "source": [
    "# exo06_03 - programme principal"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "### exo06_04 ✓✓\n",
    "\n",
    "La fonction `creaVec(n)` définie ci-dessous reçoit un argument entier `n` et retourne une liste de `n` flottants compris entre `-10` et `+10` (bornes comprises). On interprète cette liste comme un vecteur à `n` coordonnées.\n",
    "\n",
    "Recopier ce code dans une cellule et le compléter en définissant une fonction nommée `prodScal(u, v)` qui reçoit deux vecteurs ayant le même nombre de coordonnées et qui retourne leur produit scalaire (voir [exo02_11](../chapitre_02/chap02_exos.ipynb#exo02_11)), c'est-à-dire la somme des produits des coordonnées de même rang.\n",
    "\n",
    "```python\n",
    "from random import randint\n",
    "\n",
    "def creaVec(n) :\n",
    "    res = []\n",
    "    for i in range(n) :\n",
    "        res.append(randint(-20, 20) / 2)\n",
    "    return res\n",
    "```    \n",
    "\n",
    "Dans une seconde cellule, calculer :\n",
    "\n",
    "- le produit scalaire de `[1.5 , 3.0 , 0.5]` par `[2.0 , 0.0 , 2.0]` ;\n",
    "- le produit scalaire de deux vecteurs à 2 coordonnées `u1` et `u2` obtenus à l’aide de `creaVec(…)` ;\n",
    "- le produit scalaire de deux vecteurs à 3 coordonnées `v1` et `v2` obtenus à l’aide de `creaVec(…)`."
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 7,
   "metadata": {
    "collapsed": true
   },
   "outputs": [],
   "source": [
    "# exo06_04 - module"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 8,
   "metadata": {
    "collapsed": true
   },
   "outputs": [],
   "source": [
    "# exo06_04 - programme principal"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "### exo06_05 ✓✓\n",
    "\n",
    "La fonction `creaVec(n)` définie ci-dessous reçoit un argument entier `n` et retourne une liste de `n` flottants compris entre `-10` et `+10` (bornes comprises). On interprète cette liste comme un vecteur à `n` coordonnées.\n",
    "\n",
    "Recopier ce code dans une cellule et le compléter en définissant une fonction nommée `prodVec(u, v)` qui reçoit deux vecteurs ayant 3 coordonnées et qui retourne leur produit vectoriel (voir [exo02_12](../chapitre_02/chap02_exos.ipynb#exo02_12)), c'est-à-dire la liste des trois coordonnées du vecteur résultat.\n",
    "\n",
    "```python\n",
    "from random import randint\n",
    "\n",
    "def creaVec(n) :\n",
    "    res = []\n",
    "    for i in range(n) :\n",
    "        res.append(randint(-20, 20)/2)\n",
    "    return res\n",
    "```    \n",
    "\n",
    "Dans une seconde cellule, calculer :\n",
    "\n",
    "- le produit vectoriel de `[1.5 , 3.0 , 0.5]` par `[2.0 , 0.0 , 2.0]` ;\n",
    "- le produit vectoriel de `[1.5 , 3.0 , 0.5]` par `[4.5 , 9.0 , 1.5]` ;\n",
    "- le produit vectoriel de deux vecteurs à 3 coordonnées `w1` et `w2` obtenus à l’aide de `creaVec(…)`."
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 9,
   "metadata": {
    "collapsed": true
   },
   "outputs": [],
   "source": [
    "# exo06_05 - module"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 10,
   "metadata": {
    "collapsed": true
   },
   "outputs": [],
   "source": [
    "# exo06_05 - programme principal"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "### exo06_06 ✓\n",
    "\n",
    "Écrire une procédure `table` avec quatre paramètres : `base` , `debut` , `fin` et `inc`.  \n",
    "Cette procédure doit afficher la table de multiplication par `base`, de `debut` à `fin` , de `inc` en `inc` (par exemple, la table de multiplication par 4, de 3 à 8, de 1 en 1).\n",
    "\n",
    "Dans une seconde cellule, tester la procédure."
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 11,
   "metadata": {
    "collapsed": true
   },
   "outputs": [],
   "source": [
    "# exo06_06 - module"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 12,
   "metadata": {
    "collapsed": true
   },
   "outputs": [],
   "source": [
    "# exo06_06 - programme principal"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "### exo06_07 ✓\n",
    "\n",
    "Écrire une fonction `maFonction` qui retourne $f(x) = 2 x^3 + x − 5$.\n",
    "\n",
    "Écrire une procédure `tabuler` avec quatre paramètres : `fonction`, `borneInf`, `borneSup` et `nbPas` (où  `borneInf < borneSup` et `nbPas >= 2`). Cette procédure affiche les valeurs résultant de l'appel à `fonction`, avec un $x$ de `borneInf` à `borneSup`, tous les `nbPas`. \n",
    "\n",
    "Dans une seconde cellule, tester la fonction `tabuler` avec la fonction de calcul `maFonction` après avoir saisi les deux bornes et le nombre de pas."
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 13,
   "metadata": {
    "collapsed": true
   },
   "outputs": [],
   "source": [
    "# exo06_07 - module"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 14,
   "metadata": {
    "collapsed": true
   },
   "outputs": [],
   "source": [
    "# exo06_07 - programme principal"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "### exo06_08 ✓\n",
    "\n",
    "Écrire une fonction `volMasseEllipsoide()` qui reçoit un tuple de quatre paramètres (les trois demi-axes et la masse volumique) et qui retourne le volume et la masse d’un ellipsoïde. On donnera à ces quatre paramètres des valeurs par défaut.\n",
    "\n",
    "Dans une seconde cellule, tester cette fonction par des appels avec différents nombres d’arguments.\n",
    "\n",
    "**On donne :** Le volume de l'ellipsoïde est : $V = \\frac{4}{3} \\pi.a.b.c$"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 15,
   "metadata": {
    "collapsed": true
   },
   "outputs": [],
   "source": [
    "# exo06_08 - module"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 16,
   "metadata": {
    "collapsed": true
   },
   "outputs": [],
   "source": [
    "# exo06_08 - programme principal"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "### exo06_09 ✓\n",
    "\n",
    "Écrire une fonction qui convertisse en m/s et en km/h une vitesse fournie par l'utilisateur en miles/heure.\n",
    "\n",
    "Dans une seconde cellule, saisir une vitesse (positive ! Veuillez filtrer la saisie) et la convertir en utilisant votre module.\n",
    "\n",
    "Testez votre fonction avec 2,8 miles/heure (1 mile = 1609 m)."
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 17,
   "metadata": {
    "collapsed": true
   },
   "outputs": [],
   "source": [
    "# exo06_09 - module"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 18,
   "metadata": {
    "collapsed": true
   },
   "outputs": [],
   "source": [
    "# exo06_09 - programme principal"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "### exo06_10 ✓\n",
    "\n",
    "La fonction `randrange(n)` du module `random` renvoie un entier aléatoire compris entre `0` et `n-1`.\n",
    "\n",
    "Écrire un module contenant une fonction sans argument qui tire un nombre aléatoire dans l'intervalle $[0, 100]$ puis demande à l'utilisateur d'entrer un nombre dans ce même intervalle (le vérifier). La fonction retourne ces deux nombres.\n",
    "\n",
    "Écrire un programme principal qui exploite cette fonction et informe l’utilisateur si sa saisie est inférieure, égale ou supérieure au tirage aléatoire."
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 19,
   "metadata": {
    "collapsed": true
   },
   "outputs": [],
   "source": [
    "# exo06_10 - module"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 20,
   "metadata": {
    "collapsed": true
   },
   "outputs": [],
   "source": [
    "# exo06_10 - programme principal"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "### exo06_11 ✓\n",
    "\n",
    "Écrire un module contenant une fonction qui affiche chacun des éléments d'un tuple de chaînes fourni en paramètre, avec le nombre de caractères correspondant à chaque chaîne.\n",
    "\n",
    "Soit le tuple : `('Jean-Michel', 'Marc', 'Maximilien', 'Alexandre-Benoît', 'Louise', 'Vanessa')`.\n",
    "\n",
    "Écrire un programme principal qui teste votre module sur ce tuple."
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 21,
   "metadata": {
    "collapsed": true
   },
   "outputs": [],
   "source": [
    "# exo06_11 - module"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 22,
   "metadata": {
    "collapsed": true
   },
   "outputs": [],
   "source": [
    "# exo06_11 - programme principal"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "### exo06_12 ✓\n",
    "\n",
    "Écrire un module contenant la fonction `listAleaFloat(n)` qui retourne une liste de `n` flottants aléatoires dans l'intervalle : $[0, 500]$, en utilisant la fonction `random()` du module standard `random`.\n",
    "\n",
    "Dans le programme principal :\n",
    "\n",
    "- saisir un entier `n` dans l'intervalle : $[2, 100]$ ;\n",
    "- construire la liste en appelant la fonction `listAleaFloat()` ;\n",
    "- afficher **l'amplitude** du tableau (écart entre sa plus grande et sa plus petite valeur);\n",
    "- afficher la **moyenne** du tableau."
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 27,
   "metadata": {
    "collapsed": true
   },
   "outputs": [],
   "source": [
    "# exo06_12 - module"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 28,
   "metadata": {
    "collapsed": true
   },
   "outputs": [],
   "source": [
    "# exo06_12 - programme principal"
   ]
  },
  {
   "cell_type": "markdown",
   "metadata": {},
   "source": [
    "### exo06_14 ✓\n",
    "\n",
    "Écrire une fonction `minMaxMoy()` qui reçoit une liste d’entiers et qui renvoie un tuple de trois valeurs : le minimum, le maximum et la moyenne de cette liste. La fonction ne doit pas utiliser les fonctions standard `min()`, `max()` et `sum()`.\n",
    "    \n",
    "Le programme principal appellera cette fonction avec la liste : `[10, 18, 14, 20, 12, 16]`."
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 29,
   "metadata": {
    "collapsed": true
   },
   "outputs": [],
   "source": [
    "# exo06_14 - module"
   ]
  },
  {
   "cell_type": "code",
   "execution_count": 30,
   "metadata": {
    "collapsed": true
   },
   "outputs": [],
   "source": [
    "# exo06_14 - programme principal"
   ]
  }
 ],
 "metadata": {
  "kernelspec": {
   "display_name": "Python 3",
   "language": "python",
   "name": "python3"
  },
  "language_info": {
   "codemirror_mode": {
    "name": "ipython",
    "version": 3
   },
   "file_extension": ".py",
   "mimetype": "text/x-python",
   "name": "python",
   "nbconvert_exporter": "python",
   "pygments_lexer": "ipython3",
   "version": "3.7.7"
  }
 },
 "nbformat": 4,
 "nbformat_minor": 2
}
