summaryrefslogtreecommitdiff
path: root/PVCM/cama/fr/ma1 np02 Filtres.ipynb
diff options
context:
space:
mode:
Diffstat (limited to 'PVCM/cama/fr/ma1 np02 Filtres.ipynb')
-rw-r--r--PVCM/cama/fr/ma1 np02 Filtres.ipynb411
1 files changed, 411 insertions, 0 deletions
diff --git a/PVCM/cama/fr/ma1 np02 Filtres.ipynb b/PVCM/cama/fr/ma1 np02 Filtres.ipynb
new file mode 100644
index 0000000..1de9ccc
--- /dev/null
+++ b/PVCM/cama/fr/ma1 np02 Filtres.ipynb
@@ -0,0 +1,411 @@
+{
+ "metadata": {
+ "kernelspec": {
+ "display_name": "Python 3 (ipykernel)",
+ "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.8.10"
+ }
+ },
+ "nbformat": 4,
+ "nbformat_minor": 1,
+ "cells": [
+ {
+ "cell_type": "code",
+ "execution_count": 1,
+ "metadata": {},
+ "outputs": [],
+ "source": [
+ "import numpy as np"
+ ]
+ },
+ {
+ "cell_type": "markdown",
+ "metadata": {
+ "lang": "fr"
+ },
+ "source": [
+ "Regardons comment extraire des morceaux d'un tableau ou modifier seulement certaines de ses parties. Pour cela nous\n",
+ "disposons de deux outils :\n",
+ " \n",
+ "* l'extraction suivant les indices\n",
+ "* l'extraction suivant un filtre logique sur les valeurs"
+ ]
+ },
+ {
+ "cell_type": "markdown",
+ "metadata": {
+ "lang": "fr"
+ },
+ "source": [
+ "## Filtrer via les indices\n",
+ "\n",
+ "On peut extraire des valeurs d'un tableau en fonction de ses indices comme on l'a fait pour les listes. Pour chaque dimension du tableau on peut indiquer\n",
+ "\n",
+ "* la valeur de l'indice voulu (un entier)\n",
+ "* une liste d'indices `debut:fin:saut`. Ainsi `1:6:2` veut dire les valeurs impaires entre l'indice 1 et l'indice 6 exclus. Les valeurs `debut`, `fin` et `saut` sont optionnelles :\n",
+ " * `:5` donne les 5 première valeurs (indices 0,1,2,3 et 4)\n",
+ " * `3:` donne de la 4-ième à la dernière valeurs\n",
+ " * `::3` donne une valeur sur 3 du début à la fin du tableau.\n",
+ "* une liste d'indices explicite comme `[1,3,-2]` (les valeurs négatives commencent par la fin, `-2` est l'avant dernier indice)"
+ ]
+ },
+ {
+ "cell_type": "code",
+ "execution_count": 2,
+ "metadata": {},
+ "outputs": [
+ {
+ "name": "stdout",
+ "output_type": "stream",
+ "text": [
+ "[[ 0 1 2 3]\n",
+ " [ 4 5 6 7]\n",
+ " [ 8 9 10 11]] \n",
+ "\n",
+ "[4 5 6 7] \n",
+ "\n",
+ "[[0 1]\n",
+ " [4 5]] \n",
+ "\n",
+ "[ 3 11] \n",
+ "\n",
+ "[[ 0 3]\n",
+ " [ 4 7]\n",
+ " [ 8 11]]\n"
+ ]
+ }
+ ],
+ "source": [
+ "a = np.arange(12).reshape(3,4)\n",
+ "print(a, '\\n')\n",
+ "print(a[1, :], '\\n') # 2nd line\n",
+ "print(a[0:2, 0:2], '\\n') # top left sub-matrix\n",
+ "print(a[::2, -1], '\\n') # even lines, last column\n",
+ "print(a[:, [0,-1]]) # first and last column"
+ ]
+ },
+ {
+ "cell_type": "markdown",
+ "metadata": {
+ "lang": "fr"
+ },
+ "source": [
+ "Il est ainsi possible d'indiquer qu'une opération ne s'applique qu'à un extrait du tableau en indiquant \n",
+ "quelles sont les cases du tableau qui seront modifiées :"
+ ]
+ },
+ {
+ "cell_type": "code",
+ "execution_count": 3,
+ "metadata": {},
+ "outputs": [
+ {
+ "data": {
+ "text/plain": [
+ "array([[ 0, 101, 2, 103],\n",
+ " [ 4, 5, 6, 7],\n",
+ " [ 8, 109, 10, 111]])"
+ ]
+ },
+ "execution_count": 3,
+ "metadata": {},
+ "output_type": "execute_result"
+ }
+ ],
+ "source": [
+ "a[::2, 1::2] += 100\n",
+ "a"
+ ]
+ },
+ {
+ "cell_type": "markdown",
+ "metadata": {
+ "lang": "fr"
+ },
+ "source": [
+ "Cela permet aussi d'écrire simplement des calculs comme extraire une image en niveau de gris d'une image en couleur :"
+ ]
+ },
+ {
+ "cell_type": "code",
+ "execution_count": 4,
+ "metadata": {},
+ "outputs": [],
+ "source": [
+ "image = np.random.randint(256, size=(800, 600, 3)) # RGB 800x600 image\n",
+ "gray_image = 0.2126 * image[:,:,0] + 0.7152 * image[:,:,1] + 0.0722 * image[:,:,2]"
+ ]
+ },
+ {
+ "cell_type": "markdown",
+ "metadata": {
+ "lang": "fr"
+ },
+ "source": [
+ "On peut aussi utiliser `...` pour remplacer plusieurs indices ainsi `image[...,0] == image[:,:,0]`"
+ ]
+ },
+ {
+ "cell_type": "markdown",
+ "metadata": {
+ "lang": "fr"
+ },
+ "source": [
+ "## Les filtres logiques\n",
+ "\n",
+ "### Un filtre = une condition logique\n",
+ "\n",
+ "Numpy permet d'extraire simplement les valeurs qui répondent à une condition logique.\n",
+ "\n",
+ "Pour cela on utilise un filtre, à savoir un tableau booléen que l'on pose sur un tableau de même dimension en imaginant que les cases True sont des fenêtres et False des murs. Le résultat est l'ensemble des valeurs qu'on voit à travers les fenêtres ordonnées par leur indice.\n",
+ "\n",
+ "Le résultat est toujours un tableau en 1 dimension sauf si on utilise `where`."
+ ]
+ },
+ {
+ "cell_type": "code",
+ "execution_count": 5,
+ "metadata": {},
+ "outputs": [
+ {
+ "name": "stdout",
+ "output_type": "stream",
+ "text": [
+ "The filter a > 5 is\n",
+ " [[False False False False]\n",
+ " [False False True True]\n",
+ " [ True True True True]]\n"
+ ]
+ },
+ {
+ "data": {
+ "text/plain": [
+ "array([ 6, 7, 8, 9, 10, 11])"
+ ]
+ },
+ "execution_count": 5,
+ "metadata": {},
+ "output_type": "execute_result"
+ }
+ ],
+ "source": [
+ "a = np.arange(12).reshape(3,4)\n",
+ "fil = a > 5 # a > 5 means all VALUES greater than 5\n",
+ "print(\"The filter a > 5 is\\n\", fil)\n",
+ "a[fil] # apply the filter and show the result (1D array)"
+ ]
+ },
+ {
+ "cell_type": "markdown",
+ "metadata": {
+ "lang": "fr"
+ },
+ "source": [
+ "Il est bien plus simple et lisible d'écrire la condition logique là où on met normalement les indices, à savoir entre les crochets :"
+ ]
+ },
+ {
+ "cell_type": "code",
+ "execution_count": 6,
+ "metadata": {},
+ "outputs": [
+ {
+ "data": {
+ "text/plain": [
+ "array([ 6, 7, 8, 9, 10, 11])"
+ ]
+ },
+ "execution_count": 6,
+ "metadata": {},
+ "output_type": "execute_result"
+ }
+ ],
+ "source": [
+ "a[a>5]"
+ ]
+ },
+ {
+ "cell_type": "markdown",
+ "metadata": {
+ "lang": "fr"
+ },
+ "source": [
+ "#### Lorsque le but est le filtre\n",
+ "\n",
+ "Le filtre peut servir à autre chose qu'a séléctionner les valeurs de notre tableau. Il peut être le résultat sur lequel on veut travailler, par exemple pour une population `fil = (age == weight)`. C'est un tableau de booléen qui donne des cas vrai et d'autre faux c.a.d. des 0 et des 1.\n",
+ "\n",
+ "Ainsi, avec un filtre `fil`, on peut savoir\n",
+ "\n",
+ "| | | |\n",
+ "|:-|:-|:-|\n",
+ "| combien de cas sont vrai : |`fil.sum()` | |\n",
+ "| s'il y a au moins un cas vrai : |`fil.sum() > 0` | Numpy offre aussi `np.any(fil)` |\n",
+ "| si tous les cas sont vrai : |`fil.prod() == 1` | Numpy offre aussi `np.all(fil)` |\n",
+ "| si au moins un cas est faux : |`fil.prod() == 0` ||\n",
+ "| si tous les cas sont faux : | `fil.sum() == 0` ||"
+ ]
+ },
+ {
+ "cell_type": "markdown",
+ "metadata": {
+ "lang": "fr"
+ },
+ "source": [
+ "### `where` pour gérer les valeurs hors filtre\n",
+ "\n",
+ "Pour conserver la forme du tableau il est nécessaire de lui indiquer ce qu'il doit faire des valeurs qui ne remplissent pas la condition. Pour cela on utilise la fonction [`where`](https://docs.scipy.org/doc/numpy/reference/generated/numpy.where.html) :"
+ ]
+ },
+ {
+ "cell_type": "code",
+ "execution_count": 7,
+ "metadata": {},
+ "outputs": [
+ {
+ "data": {
+ "text/plain": [
+ "array([[ 0, 0, 0, 0],\n",
+ " [ 0, 0, 6, 7],\n",
+ " [ 8, 9, 10, 11]])"
+ ]
+ },
+ "execution_count": 7,
+ "metadata": {},
+ "output_type": "execute_result"
+ }
+ ],
+ "source": [
+ "np.where(a > 5, a, 0) # if a > 5 then a else 0"
+ ]
+ },
+ {
+ "cell_type": "markdown",
+ "metadata": {
+ "lang": "fr"
+ },
+ "source": [
+ "On peut faire tous les filtres imaginables qui donnent un tableau de booléan."
+ ]
+ },
+ {
+ "cell_type": "code",
+ "execution_count": 8,
+ "metadata": {},
+ "outputs": [
+ {
+ "data": {
+ "text/plain": [
+ "array([[ 0, -1, -1, 6],\n",
+ " [-1, -1, 12, -1],\n",
+ " [-1, 18, -1, -1]])"
+ ]
+ },
+ "execution_count": 8,
+ "metadata": {},
+ "output_type": "execute_result"
+ }
+ ],
+ "source": [
+ "np.where(a%3 == 0, 2*a, -1) # if a modulo 3 is 0 then 2 times a else -1"
+ ]
+ },
+ {
+ "cell_type": "markdown",
+ "metadata": {
+ "lang": "fr"
+ },
+ "source": [
+ "### Mettre à jour un tableau avec un filtre\n",
+ "\n",
+ "Une autre facon de conserver la forme du tableau consiste à ne modifier que les valeurs qui correspondent au filtre."
+ ]
+ },
+ {
+ "cell_type": "code",
+ "execution_count": 9,
+ "metadata": {},
+ "outputs": [
+ {
+ "data": {
+ "text/plain": [
+ "array([[ 0, 1, 2, 3],\n",
+ " [ 4, 5, 200, 200],\n",
+ " [200, 200, 200, 200]])"
+ ]
+ },
+ "execution_count": 9,
+ "metadata": {},
+ "output_type": "execute_result"
+ }
+ ],
+ "source": [
+ "a = np.arange(12).reshape(3,4)\n",
+ "a[a > 5] = 200\n",
+ "a"
+ ]
+ },
+ {
+ "cell_type": "markdown",
+ "metadata": {
+ "lang": "fr"
+ },
+ "source": [
+ "Voici comment ajouter 100 à toutes les valeurs du tableau qui sont des carrés parfait ainsi qu'à la valeur 5 :"
+ ]
+ },
+ {
+ "cell_type": "code",
+ "execution_count": 10,
+ "metadata": {},
+ "outputs": [
+ {
+ "data": {
+ "text/plain": [
+ "array([[100, 101, 2, 3],\n",
+ " [104, 105, 6, 7],\n",
+ " [ 8, 109, 10, 11]])"
+ ]
+ },
+ "execution_count": 10,
+ "metadata": {},
+ "output_type": "execute_result"
+ }
+ ],
+ "source": [
+ "a = np.arange(12).reshape(3,4)\n",
+ "a[(np.round(np.sqrt(a)) - np.sqrt(a) == 0) | (a==5)] += 100 # | is OR (AND is &)\n",
+ "a"
+ ]
+ },
+ {
+ "cell_type": "markdown",
+ "metadata": {
+ "variables": {
+ " PreviousNext(\"np01 Numpy Introduction.ipynb\", \"np03 Manipulations.ipynb\")": "&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <br/><center><a href=\"np01 Numpy Introduction.ipynb\">np01 Numpy Introduction</a>&nbsp; ← <a href=\"http://python3.mooc.lrde.epita.fr/notebooks/Table%20des%20mati%C3%A8res.ipynb\" style=\"text-decoration:none\"> △ </a> → &nbsp;<a href=\"np03 Manipulations.ipynb\">np03 Manipulations</a></center><br/>&nbsp;"
+ }
+ },
+ "source": [
+ "{{ PreviousNext(\"np01 Numpy Introduction.ipynb\", \"np03 Manipulations.ipynb\")}}"
+ ]
+ },
+ {
+ "cell_type": "code",
+ "execution_count": null,
+ "metadata": {},
+ "outputs": [],
+ "source": []
+ }
+ ]
+} \ No newline at end of file