Commit 954306da authored by Matthieu Boileau's avatar Matthieu Boileau
Browse files

Up 05

parent 029e0b74
Pipeline #15782 passed with stages
in 1 minute and 30 seconds
%% Cell type:markdown id: tags:
# Microprojet
![](fig/python-logo.png)
- Utiliser les modules de la bibliothèque standard pour récupérer des données via un service web.
- Manipuler les dictionnaires et les chaînes de caractères
- Utiliser la bibliothèque de tracés graphiques matplotlib
- Utiliser un IDE (Spyder)
- Exécuter un fichier script
- Gérer les arguments de la ligne de commande
%% Cell type:markdown id: tags:
## Exercice
Exploiter les données du site [http://www.prevision-meteo.ch](http://www.prevision-meteo.ch) pour tracer l'évolution horaire de la température à Strasbourg aujourd'hui.
![](fig/icon.png)
%% Cell type:markdown id: tags:
### Ouverture du fichier de prévisions
Le site [https://www.prevision-meteo.ch](https://www.prevision-meteo.ch) fournit des prévisions sous forme de fichier au format [json](https://fr.wikipedia.org/wiki/JavaScript_Object_Notation). On veut récupérer les données relatives à Strasbourg avec la méthode `urlopen()` du module `urllib.request`.
%% Cell type:code id: tags:
```
%config InlineBackend.figure_format = 'retina'
%matplotlib inline
from urllib.request import urlopen
jsonfile_url = "https://www.prevision-meteo.ch/services/json/Strasbourg"
try:
f = urlopen(jsonfile_url, timeout=10) # open url
except:
except Exception:
print("Le téléchargement a échoué : on lit une version locale.")
f = open("exos/Strasbourg.json")
```
%% Cell type:markdown id: tags:
### Chargement du fichier json ouvert
%% Cell type:markdown id: tags:
La méthode `json.loads()` permet de charger un fichier json comme un dictionnaire python :
%% Cell type:code id: tags:
```
import json
jsondict = json.loads(f.read()) # Read JSON file
```
%% Cell type:markdown id: tags:
### Exploration des données
On commence naïvement par afficher le contenu du fichier :
%% Cell type:code id: tags:
```
print(type(jsondict))
print(jsondict)
```
%% Cell type:markdown id: tags:
On essaie de faire mieux en affichant uniquement les clés du dictionnaire :
%% Cell type:code id: tags:
```
for k in jsondict:
print(repr(k))
```
%% Cell type:markdown id: tags:
On est intéressé par le temps d'aujourd'hui :
%% Cell type:code id: tags:
```
day = jsondict['fcst_day_0']
print(day)
```
%% Cell type:markdown id: tags:
Là aussi, on cherche les clés :
%% Cell type:code id: tags:
```
for k in day:
print(repr(k))
```
%% Cell type:markdown id: tags:
Vérifions qu'il s'agit d'aujourd'hui :
%% Cell type:code id: tags:
```
print(day['day_long'], day['date'])
```
%% Cell type:markdown id: tags:
C'est bon !
Maintenant, une entrée particulière nous intéresse :
%% Cell type:code id: tags:
```
day_hd = day['hourly_data']
for k in day_hd:
print(repr(k))
```
%% Cell type:markdown id: tags:
Regardons ce que contient une `hourly_data` :
%% Cell type:code id: tags:
```
for k in day_hd['8H00']:
print(repr(k))
```
%% Cell type:markdown id: tags:
La clé qui nous intéresse est la chaîne `'TMP2m'` qui correspond à la température à 2m du sol.
%% Cell type:code id: tags:
```
hour = '12H00'
print(f"Aujourd'hui à {hour}, il fera : {day_hd[hour]['TMP2m']} deg. C.")
```
%% Cell type:markdown id: tags:
Sauver ces lignes de commandes dans le fichier `today_stras.py` en allant de l'exécution 1 au compteur d'exécution courant indiqué dans la cellule de code ci-dessus `In [XX]`. Dans le cas présent :
%% Cell type:code id: tags:
```
# Décommenter la ligne ci-dessous
%save today_stras.py 1-12
```
%% Cell type:markdown id: tags:
### Tracé de la température
1. Ouvrir le fichier `today_stras.py` dans Spyder et nettoyer les `print` inutiles.
2. Exécutez le code dans Spyder et utilisez la fenêtre "Variable explorer" en haut à droite pour parcourir les données de votre dictionnaire.
3. Extraire la liste des couples `(hour, temperature)` où :
- `hour` est un entier
- `temperature` est un flottant
4. ordonner la liste selon les heures croissantes
5. convertir la liste en un *numpy array* `t` avec la méthode `numpy.array()`
6. Transposer `t` pour obtenir le tableau `[[array of hours], [array of temperatures]]`
7. réaliser un tracé matplotlib en suivant [ce tutoriel](http://matplotlib.org/users/pyplot_tutorial.html) ou en intégrant les lignes de code suivantes :
%% Cell type:code id: tags:
```
import matplotlib.pyplot as plt # To be placed at the top of python file
# [Your previous code...]
# Plot T = T(hour)
# Décommentez les lignes ci-dessous
#
# fig = plt.figure() # initialise figure
# title = f"{day_of_the_week} {date_of_today}"
# fig.suptitle(title, fontsize=14, fontweight='bold')
#
# ax = fig.add_subplot(111) # initialise a plot area
# fig.subplots_adjust(top=0.85)
# ax.set_title('Day temperature')
# ax.set_xlabel('Time [h]')
# ax.set_ylabel('Temperature [deg. C]')
#
# ax.plot(t[0], t[1]) # plot t[1] (tempe) as a function of t[0] (hour)
```
%% Cell type:markdown id: tags:
> **Option :** intégrer l'icone de la météo du jour en utilisant le module `matplotlib.image`.
%% Cell type:markdown id: tags:
Pas si vite ! Êtes-vous sûr ? Vraiment ?
Alors rendez-vous dans [exos/meteo_json.py](exos/meteo_json.py)
%% Cell type:markdown id: tags:
## Exercice sur les fonctions
Modifiez le programme météo en créant une fonction qui admet un des jours disponibles comme argument (aujourd'hui, demain, après-demain...)
%% Cell type:markdown id: tags:
Pas si vite ! Êtes-vous sûr ? Vraiment ?
Alors allez voir une proposition de solution dans [exos/meteo_json_func.py](exos/meteo_json_func.py)
%% Cell type:markdown id: tags:
## Exécution avec les widgets ipython
[Jupyter ipywidgets](https://ipywidgets.readthedocs.io/en/latest/index.html) permet de créer très facilement des menus interactifs pour faciliter l'exécution de code dans les notebooks.
%% Cell type:markdown id: tags:
Un exemple avec notre courbe de température :
%% Cell type:code id: tags:
```
from exos import meteo_json_func as mjf
from ipywidgets import interact
def plot_city(city_name, iday):
city_json = mjf.get_json_from_name(city_name)
mjf.plot_day_tempe(city_json, f'fcst_day_{iday}')
interact(plot_city,
city_name=["Marseille", "Paris", "Toulouse", "Strasbourg"],
iday=list(range(5)));
```
%% Cell type:markdown id: tags:
## Exécution en script
Pour pouvoir exécuter ce fichier en mode script
- Ajouter en première ligne du fichier: `#! python3`
- Rendez le fichier exécutable: `chmod a+x today_stras.py`
%% Cell type:code id: tags:
```
# pour permettre le tracé de la figure dans le notebook :
%matplotlib inline
# équivalent à exécuter la commande :
# python3 exos/meteo_json.py
# depuis le terminal système, décommentez et exécutez :
#%run exos/meteo_json.py
```
%% Cell type:markdown id: tags:
### Utilisation de `if __name__ == '__main__':`
Dans un fichier python `mon_module.py`, on souhaite généralement différencier :
- le code exécuté lors d'un import du fichier comme un module dans un autre programme avec `import mon_module`
- le code éxécuté lorsque le fichier est appelé directement comme un script depuis le système : `python mon_module.py`
Pour ce faire, on utilise la variable `__name__` de la façon suivante :
%% Cell type:code id: tags:
```
#! python3
def une_fonction_utile():
return 'je suis utile'
def main():
print('je suis dans {}'.format(__name__))
if __name__ == '__main__':
main()
else:
# En mode module importé, on ne fait rien de plus
pass
```
%% Cell type:markdown id: tags:
## Gestion des arguments
Pour pouvoir passer des arguments en ligne de commande, on peut utiliser le module [`argparse`](https://docs.python.org/3/library/argparse.html).
Un tutoriel est disponible [ici](https://docs.python.org/3/howto/argparse.html#argparse-tutorial).
%% Cell type:code id: tags:
```
import argparse
parser = argparse.ArgumentParser(description='Process some integers.')
parser.add_argument('integers', metavar='N', type=int, nargs='+',
help='an integer for the accumulator')
parser.add_argument('--sum', dest='accumulate', action='store_const',
const=sum, default=max,
help='sum the integers (default: find the max)')
print(type(parser))
```
%% Cell type:code id: tags:
```
# Sans "--sum"
args = parser.parse_args(['2', '5'])
print(args.accumulate(args.integers))
```
%% Cell type:code id: tags:
```
# Avec "--sum"
args = parser.parse_args(['--sum', '2', '5'])
print(args.accumulate(args.integers))
```
%% Cell type:code id: tags:
```
# Certains arguments existent déjà
try:
parser.parse_args(['--help'])
except SystemExit:
# Pour éviter une erreur dans jupyter-notebook
pass
```
%% Cell type:markdown id: tags:
## Exercice
Modifiez le programme météo pour qu'il prenne le(s) nom(s) de ville en argument(s) en utilisant le module `argparse`.
%% Cell type:code id: tags:
```
# Décommentez la ligne ci-dessous
#%run exos/meteo_json_func_args.py Marseille -d 3
```
%% Cell type:markdown id: tags:
Pas si vite ! Êtes-vous sûr ? Vraiment ?
Alors allez voir une proposition de solution dans [exos/meteo_json_func_args.py](exos/meteo_json_func_args.py)
%% Cell type:markdown id: tags:
## Suite de l'exercice
- Laissez libre cours à vos idées et envies, par exemple :
- en cherchant à tracer l'évolution horaire de la température dans les 5 prochains jours
- etc.
- Dans Spyder :
- testez le système de debugging
- testez le profiler
> À vous de faire la pluie et le beau temps !
......
Supports Markdown
0% or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment