Les deux révisions précédentesRévision précédenteProchaine révision | Révision précédente |
issue142:python [2019/02/26 19:46] – d52fr | issue142:python [2019/03/06 17:42] (Version actuelle) – andre_domenech |
---|
I'm going to try to show you how to use Pandas and Python, how to deal with data without ever having to open the dataset in a spreadsheet even if there are some cells that don't contain good data, using some of the tricks we learned over the last two months, and giving you some new skills at the same time.** | I'm going to try to show you how to use Pandas and Python, how to deal with data without ever having to open the dataset in a spreadsheet even if there are some cells that don't contain good data, using some of the tricks we learned over the last two months, and giving you some new skills at the same time.** |
| |
Quand les enfants doivent-ils apprendre des mots ? | Quand les enfants apprennent-ils vraiment des mots ? |
| |
Ce mois-ci, nous allons regarder un jeu de données différent. Celui que nous avons utilisé le mois dernier était, en majeure partie, parfait et complet. Cependant, ce n'est pas comme ça que ça marche dans le monde réel. Des données manqueront dans des champs, ou n'auront aucun sens par rapport au sujet que les données sont censées couvrir. Souvent, les données que nous trouvons vraiment sont manquantes ou mauvaises et elles faussent les résultats. | Ce mois-ci, nous allons regarder un jeu de données différent. Celui que nous avons utilisé le mois dernier était, en majeure partie, parfait et complet. Cependant, ce n'est pas comme ça que ça marche dans le monde réel. Des données manqueront dans des champs, ou n'auront aucun sens par rapport au sujet que les données sont censées couvrir. Souvent, les données que nous trouvons en fait sont manquantes ou mauvaises et elles faussent les résultats. |
| |
Je vais essayer de vous montrer comment utiliser Pandas et Python, comment traiter les données sans jamais à avoir à ouvrir le jeu de données dans un tableur, même si certaines cellules ne contiennent pas des données correctes, en utilisant quelques astuces que nous avons apprises dans les deux derniers mois, et en vous donnant en même temps quelques nouvelles compétences. | Je vais essayer de vous montrer comment utiliser Pandas et Python, comment traiter les données sans jamais devoir ouvrir le jeu de données dans un tableur - même si certaines cellules ne contiennent pas des données correctes -, en utilisant quelques astuces que nous avons apprises dans les deux derniers mois, et en vous donnant en même temps quelques nouvelles compétences. |
| |
**We'll use a dataset with some missing data. This dataset can be found on kaggle.com under the heading 'When Do Children Learn Words - Information on when Norwegian children generally learn words'. The actual URL is https://www.kaggle.com/rtatman/when-do-children-learn-words. When getting data from web sources, sometimes they give you a good amount of information about the dataset, sometimes not so much. In this case, there is a pretty good writeup about the data. If you look at the tabs just under the picture, you will see that the second tab from the left is titled 'Overview'. That tab has a list of the column names and their content. This information is key to understanding what the data is really about and what we can expect to find. We will discuss the various columns in a moment. You should download the file 'main_data.csv' – the other csv file is optional, we won't be looking at it in this article. | **We'll use a dataset with some missing data. This dataset can be found on kaggle.com under the heading 'When Do Children Learn Words - Information on when Norwegian children generally learn words'. The actual URL is https://www.kaggle.com/rtatman/when-do-children-learn-words. When getting data from web sources, sometimes they give you a good amount of information about the dataset, sometimes not so much. In this case, there is a pretty good writeup about the data. If you look at the tabs just under the picture, you will see that the second tab from the left is titled 'Overview'. That tab has a list of the column names and their content. This information is key to understanding what the data is really about and what we can expect to find. We will discuss the various columns in a moment. You should download the file 'main_data.csv' – the other csv file is optional, we won't be looking at it in this article. |
If you open 'main_data.csv' in your favorite text editor, you will see something like that shown below.** | If you open 'main_data.csv' in your favorite text editor, you will see something like that shown below.** |
| |
Nous utiliserons un jeu de données avec des données manquantes. Ce jeu de données peut être trouvé sur kaggle.com sous l'entête « When Do Children Learn Words - Information on when Norwegian children generally learn words (Quand les enfants apprennent-ils vraiment des mots ? - Informations sur la manière dont les enfants norvégiens apprennent des mots en général). En récupérant des données depuis des sources sur le Web, celles-ci vous donnent parfois une bonne quantité d'informations à propos du jeu de données, parfois beaucoup moins. De notre cas, il y a un plutôt bon texte sur les données. Si vous regadez les onglets juste sous l'image, vous verrez que le deuxième onglet à partir de la gauche est intitulé « Overview » (Présentation). Cette onglet a une liste des noms des colonnes et de leur contenu. C'est une information-clé pour comprendre ce que sont vraiment ces données et ce que nous pouvons espérer trouver. Nous présenterons les différentes colonnes dans un moment. Vous devrez télécharger le fichier « main_data.csv » l'autre fichier csv est optionnel, nous ne le regarderons pas dans cet article. | Nous utiliserons un jeu de données avec des données manquantes. Ce jeu de données peut être trouvé sur kaggle.com sous l'entête « When Do Children Learn Words - Information on when Norwegian children generally learn words » (Quand les enfants apprennent-ils vraiment des mots ? - Informations sur la manière dont les enfants norvégiens apprennent des mots en général.) L'URL véritable est https://www.kaggle.com/rtatman/when-do-children-learn-words. En récupérant des données depuis des sources sur le Web, vous aurez parfois une bonne quantité d'informations à propos du jeu de données, parfois beaucoup moins. Dans notre cas, il y a un assez bon texte sur les données. Si vous regardez les onglets juste sous l'image, vous verrez que le deuxième onglet à partir de la gauche est intitulé « Overview » (Présentation). Cet onglet a une liste des noms des colonnes et de leur contenu. C'est une information-clé pour comprendre ce que couvrent vraiment ces données et ce que nous pouvons espérer trouver. Nous présenterons les différentes colonnes dans un moment. Vous devrez télécharger le fichier « main_data.csv », l'autre fichier csv est optionnel et nous ne le regarderons pas dans cet article. |
| |
Si vous ouvrez le fichier « main_data.csv » dans votre éditeur de texte favori, vous verrez quelque chose comme ce qui est présenté ci-dessous. | Si vous ouvrez le fichier « main_data.csv » dans votre éditeur de texte favori, vous verrez quelque chose comme ce qui est présenté ci-dessous. |
Next page, top right, is the breakdown of the columns and their meanings.** | Next page, top right, is the breakdown of the columns and their meanings.** |
| |
Je suis sûr que vous réalisez que je ne vous ai montré ici que les 5 premières lignes du fichier, mais cela vous donne une idée assez bonne de ce que nous regarderons. Si vous n'avez jamais vu avant un fichier .csv dans un éditeur de texte, vous verrez que (dans ce cas-ci) la première ligne montre les noms des colonnes, séparés par des virgules, et qu'il y aura 11 colonnes de données. Vous pouvez aussi descendre vers le bas de la liste et voir qu'il y a 732 lignes, ce qui veut dire 731 lignes de données. | Je suis sûr que vous réalisez que je ne vous ai montré ici que les 5 premières lignes du fichier, mais cela vous donne une idée assez bonne de ce que nous regarderons. Si vous n'avez jamais vu de fichier .csv dans un éditeur de texte, vous verrez que (dans ce cas-ci) la première ligne montre les noms des colonnes, séparés par des virgules, et qu'il y aura 11 colonnes de données. Vous pouvez aussi descendre vers le bas de la liste et voir qu'il y a 732 lignes, ce qui veut dire 731 lignes de données. |
| |
Si vous regardez la quatrième ligne du fichier, vous verrez que l'avant-dernier champ a « #N/A » au lieu d'un chiffre. Vous pouvez penser que « #N/A » signifie « Not available » (non disponible) ou « Not applicable » (non applicable). (Je préfère le premier.) | Si vous regardez la quatrième ligne du fichier, vous verrez « #N/A » dans l'avant-dernier champ au lieu d'un chiffre. Vous pouvez penser que « #N/A » signifie « Not available » (non disponible) ou « Not applicable » (non applicable). (Je préfère le premier.) |
| |
À la page suivante, en haut à droite, sont présentés les entêtes de colonnes et leur signification. | À la page suivante, en haut à droite, sont présentés les entêtes de colonnes et leur signification. |
print(df.isnull().sum(axis=0))** | print(df.isnull().sum(axis=0))** |
| |
Bien ! Pour ce article en particulier, nous nous intéresserons aux colonnes suivantes... | Bien ! Pour cet article précis, nous nous intéresserons aux colonnes suivantes... |
| |
« Word_NW », « Translation », « AoA », « VSoA », « Lex_cat », « Freq », « CDS_freq » | « Word_NW », « Translation », « AoA », « VSoA », « Lex_cat », « Freq », « CDS_freq » |
| |
où se trouvent le mot norvégien, sa traduction en anglais, l'age de l'enfant quand il apprend le mot, le nombre d'autres mots qu'il connaît généralement alors, la catégorie du mot, si ce mot est courant en norvégien et si ce mot est souvent utilisé quand un adulte parle à un enfant. | où se trouvent le mot norvégien, sa traduction en anglais, l'âge de l'enfant quand il apprend le mot, le nombre d'autres mots qu'il connaît généralement, la catégorie du mot, si ce mot est courant en norvégien et si ce mot est souvent utilisé quand un adulte parle à un enfant. |
| |
Maintenant que nous savons ce que nous avons, et ce qui va nous intéresser, allons-y. Créez un répertoire pour votre projet et copiez dedans le fichier main_data.csv,ouvrez un terminal, changer pour ce répertoire, et lancez votre shell Python. Maintenant, importez pandas comme vous le fîtes le mois dernier et créez une Dataframe que nous pourrons utiliser avec... | Maintenant que nous savons ce que nous avons, et ce qui va nous intéresser, allons-y. Créez un répertoire pour votre projet et copiez-y le fichier main_data.csv, ouvrez un terminal, changez pour ce répertoire, et lancez votre shell Python. Maintenant, importez pandas comme vous l'avez fait le mois dernier et créez une DataFrame que nous pourrons utiliser : |
| |
import pandas as pd | import pandas as pd |
| |
csvfile = 'main_data.csv' | csvfile = 'main_data.csv' |
rawdata = pd.read_csv(csvfile) | rawdata = pd.read_csv(csvfile) |
| |
# Créer notre Dataframe simple du début | # Créer notre DataFrame simple du début |
| |
df = pd.DataFrame(rawdata) | df = pd.DataFrame(rawdata) |
| |
Maintenant que notre Dataframe est en place, nous devons connaître qu'elle est la part de « mauvaises » données. Nous pouvons le faire avec la déclaration suivante en Python... | Maintenant que notre DataFrame est en place, nous devons connaître jusqu'à quel point les données sont « mauvaises ». Nous pouvons le faire avec la déclaration suivante en Python : |
| |
print(df.isnull().sum(axis=0)) | print(df.isnull().sum(axis=0)) |
Now, the next question would be what to do with those null values. We can simply replace the null values with the mean or average of the "real" values in each numerical column we are interested in, and ‘unknown’ in the text column. It WILL skew the data a little bit, but we should be able to live with that.** | Now, the next question would be what to do with those null values. We can simply replace the null values with the mean or average of the "real" values in each numerical column we are interested in, and ‘unknown’ in the text column. It WILL skew the data a little bit, but we should be able to live with that.** |
| |
Je suis allé sur Internet pour trouver une explication simple du paramètre « axis » et, grâce à un message sur StackOverFlow, la réponse « facile » est que axis=0 est l'ensemble des données de toutes les lignes dans chaque colonne et que axis=1 est celui des données de toutes les colonnes dans chaque ligne. Aussi, la requête signifie : donnez-moi la somme de toutes les valeurs nulles de chaque colonne de notre Dataframe. | Je suis allé sur Internet pour trouver une explication simple du paramètre « axis » et, grâce à un message sur StackOverFlow, la réponse « facile » est que axis=0 est l'ensemble des données de toutes les lignes dans chaque colonne et que axis=1 est celui des données de toutes les colonnes dans chaque ligne. Ainsi, la requête signifie : donnez-moi la somme de toutes les valeurs nulles de chaque colonne de notre Dataframe. |
| |
Cette « requête » nous donne la sortie suivante... | Cette « requête » nous donne la sortie suivante : |
| |
ID_CDI_I 341 | ID_CDI_I 341 |
dtype: int64 | dtype: int64 |
| |
Maintenant, la question suivante est quoi faire de ces valeurs nulles. Nous pouvons simplement remplacer les valeurs nulles par la médiane ou la moyenne des valeurs « utiles » dans chaque colonne numérique qui nous intéresse, et par « inconnu » dans les colonnes de texte. Ça faussera un peu les données, mais nous devrions pouvoir vivre avec. | Maintenant, la question suivante est : que faire de ces valeurs nulles ? Nous pouvons simplement remplacer les valeurs nulles par la médiane ou la moyenne des valeurs « utiles » dans chaque colonne numérique qui nous intéresse, et par « inconnu » dans les colonnes de texte. Ça faussera un peu les données, mais nous devrions pouvoir vivre avec. |
| |
**So, rather than mess with our main DataFrame, we'll create one that contains only the columns we are interested in, then fix the data there. First, we'll create a list of the column names we are interested in... | **So, rather than mess with our main DataFrame, we'll create one that contains only the columns we are interested in, then fix the data there. First, we'll create a list of the column names we are interested in... |
5434: SettingWithCopyWarning: A value is trying to be set on a copy of a slice from a DataFrame** | 5434: SettingWithCopyWarning: A value is trying to be set on a copy of a slice from a DataFrame** |
| |
Aussi, plutôt que ce foutoir qu'est notre Dataframe, nous en créerons une qui ne contient que les colonnes qui nous intéressent, puis nous résoudrons le problème des données plus tard. D'abord, créons une listes des noms de colonnes qui nous intéressent... | Aussi, au lieu d'utiliser le bazar qu'est notre Dataframe, nous en créerons une qui ne contient que les colonnes qui nous intéressent, puis nous y résoudrons le problème des données. D'abord, créons une liste des noms de colonnes qui nous intéressent : |
| |
cols_to_use = ['Word_NW','Translation','AoA','VSoA','Lex_cat','Freq','CDS_freq'] | cols_to_use = ['Word_NW','Translation','AoA','VSoA','Lex_cat','Freq','CDS_freq'] |
| |
Maintenant, créons une nouvelle Dataframe avec ces seules colonnes... | Maintenant, créons une nouvelle DataFrame avec ces seules colonnes : |
| |
df2 = df[cols_to_use] | df2 = df[cols_to_use] |
df2['AoA'].fillna(df2['AoA'].mean(),inplace=True) | df2['AoA'].fillna(df2['AoA'].mean(),inplace=True) |
| |
Cependant, ceci nous donne une message d'avertissement... | Cependant, ceci nous donne un avertissement : |
| |
5434: SettingWithCopyWarning: A value is trying to be set on a copy of a slice from a DataFrame (Une valeur est en train d'être mise sur une copie d'une partie d'une Dataframe) | 5434: SettingWithCopyWarning: A value is trying to be set on a copy of a slice from a DataFrame (Une valeur est en train d'être mise sur une copie d'une partie d'une Dataframe) |
However, if we are running this in script from an IDE, this will fail and only the last 5 commands will work. There is a command that we could use...** | However, if we are running this in script from an IDE, this will fail and only the last 5 commands will work. There is a command that we could use...** |
| |
Voyez les problèmes dans la documentation : http://pandas.pydata.org/pandas-docs/stable/indexing.html#indexing-view-versus-copy | Voyez les mises en garde dans la documentation : http://pandas.pydata.org/pandas-docs/stable/indexing.html#indexing-view-versus-copy |
| |
self._update_inplace(new_data) | self._update_inplace(new_data) |
| |
Ceci est dû ce qui est appelé un affectation en chaîne. Maintenant, nous savons que c"est avec une copie que nous allons travailler ; aussi, nous pouvons sans risque remercier Pandas pour son avertissement, et relancer la commande. Cette, fois, elle marche. Maintenant, tratons les colonnes numériques restantes... | Ceci est dû à ce qui est appelé une affectation en chaîne. Nous savons que c'est avec une copie que nous allons travailler ; aussi, nous pouvons sans risque remercier Pandas pour son avertissement, et relancer la commande. Cette fois-ci, elle marche. Maintenant, traitons les colonnes numériques restantes : |
| |
df2['AoA'].fillna(df2['AoA'].mean(),inplace=True) | df2['AoA'].fillna(df2['AoA'].mean(),inplace=True) |
df2['Lex_cat'].fillna('unknown',inplace=True) | df2['Lex_cat'].fillna('unknown',inplace=True) |
| |
Cependant, si nous lançons ceci dans un script depuis l'environnement de développement, elle plante et seules les 5 dernières commandes fonctionneront. Il y a une commande que nous pouvons utiliser... | Cependant, si nous lançons ceci dans un script depuis un environnement de développement, il plante et seules les 5 dernières commandes fonctionneront. Il y a une commande que nous pouvons utiliser : |
| |
**df2.is_copy = False | **df2.is_copy = False |
df2.is_copy = False | df2.is_copy = False |
| |
Mais, elle est maintenant obsolète ; elle peut marcher aujourd'hui, mais pas demain. L'attribut « is_copy » est obsolète et sera supprimé dans une version future. | Mais, elle est maintenant obsolète ; elle fonctionnera éventuellement aujourd'hui, mais pas demain. Et nous aurons à nouveau un avertissement si on le fait : |
| |
site-packages/pandas/core/generic.py:4388: FutureWarning: Attribute 'is_copy' is deprecated and will be removed in a future version. (L'attribut « is_copy » est obsolète et sera supprimé dans une version future) | site-packages/pandas/core/generic.py:4388: FutureWarning: Attribute 'is_copy' is deprecated and will be removed in a future version. (L'attribut « is_copy » est obsolète et sera supprimé dans une version future.) |
| |
object.__getattribute__(self, name) | object.__getattribute__(self, name) |
return object.__setattr__(self, name, value) | return object.__setattr__(self, name, value) |
| |
À nouveau, cela marche aujourd'hui, mais nous ne savons pas pour combien de temps. Aussi, la voie la plus simple pour contourner ce problème est de désactiver tous les avertissements, à nouveau, pour une utilisation dans un script. | À nouveau, cela fonctionne bien aujourd'hui, mais nous ne savons pas pour combien de temps. Aussi, on peut contourner ce problème simplement en désactivant tous les avertissements si c'est pour une utilisation dans un script. |
| |
**pd.set_option('mode.chained_assignment', None) | **pd.set_option('mode.chained_assignment', None) |
| |
Now, finally, we have mostly clean data that we can work with. Make your terminal pretty wide so we can see all our data at one time (next page, top) and let's do our first query of the DataFrame and find out how many words the typical Norwegian child knows by the age of 18 months and what they are...** | Now, finally, we have mostly clean data that we can work with. Make your terminal pretty wide so we can see all our data at one time (next page, top) and let's do our first query of the DataFrame and find out how many words the typical Norwegian child knows by the age of 18 months and what they are...** |
| |
| pd.set_option('mode.chained_assignment', None) |
| |
| Cela étant dit, n'utilisez pas cette commande à moins que vous ne soyez complètement sûr que vous la comprenez. |
| |
| Enfin, assurez-vous que nous avons tout traité en lançant à nouveau notre requête de somme : |
| |
| print(df2.isnull().sum(axis=0)) |
| |
| Word_NW 0 |
| Translation 0 |
| AoA 0 |
| VSoA 0 |
| Lex_cat 0 |
| Freq 0 |
| CDS_freq 0 |
| dtype: int64 |
| |
| Maintenant, enfin, nous avons presque entièrement nettoyé les données avec lesquelles nous voulons travailler. Assurez-vous que votre terminal est grandement ouvert de sorte que vous puissiez voir toutes nos données d'un coup (page suivante, en haut) et faisons notre première requête sur la DataFrame pour découvrir combien de mots, et lesquels, un enfant norvégien typique connaît à l'age de 18 mois : |
| |
**print(df2[df2.AoA < 18]) | **print(df2[df2.AoA < 18]) |
| |
So all you Daddies out there can take heart that your name is (on average) the third word a child learns, and don't let the fact that 'vroom' usually comes before you get you down. 'Vroom' is SUCH a fun sound to make.** | So all you Daddies out there can take heart that your name is (on average) the third word a child learns, and don't let the fact that 'vroom' usually comes before you get you down. 'Vroom' is SUCH a fun sound to make.** |
| |
| print(df2[df2.AoA < 18]) |
| |
| C'est plutôt sympa, mais ça serait mieux si la sortie était triée d'après la colonne de l'age moyen (« AoA » - voir page suivante, en bas). Nous pouvons le faire de cette façon : |
| |
| print(df2[df2.AoA < 18].sort_values('AoA',ascending=True)) |
| |
| C'est beaucoup mieux. Ainsi, entre 12 et 13 mois, l'enfant norvégien moyen connaît entre 20 et 40 mots. Si vous voulez la trier à la fois sur la colonne « AoA » et sur la colonne « VSoA » (2 pages plus loin, en haut), vous pouvez le faire ainsi : |
| |
| print(df2[df2.AoA < 18].sort_values(['AoA','VSoA'],ascending=True)) |
| |
| Comme ça, vous les papas qui traînez par ici, vous pouvez être rassurés car votre nom est (en moyenne) le troisième mot que l'enfant apprend et le fait que « vroom » vienne avant ne doit pas vous décourager. « Vroom » est un son SI amusant à faire. |
| |
**To make life easier for you all, I've created a full script that does everything we just did and threw in some wait-for-keypress statements, so you can visualize the data. It is on Pastebin at https://pastebin.com/fb4pH23H | **To make life easier for you all, I've created a full script that does everything we just did and threw in some wait-for-keypress statements, so you can visualize the data. It is on Pastebin at https://pastebin.com/fb4pH23H |
| |
I'll leave you with this information and let you experiment on your own. Next time, we'll dust off some of our Page skills and create a GUI that will make it easier to play with data using a very powerful custom widget called 'pandastable'. Until then, have fun and keep learning.** | I'll leave you with this information and let you experiment on your own. Next time, we'll dust off some of our Page skills and create a GUI that will make it easier to play with data using a very powerful custom widget called 'pandastable'. Until then, have fun and keep learning.** |
| |
| Pour vous simplifier la vie, j'ai créé un script complet qui fait tout ce que nous venons de faire et j'ai mis dedans quelques déclarations attendre-l'appui-d'une-touche, pour que vous puissiez voir les données. C'est sur Pastebin à https://pastebin.com/fb4pH23H |
| |
| Je vous quitte avec cette information et vous laisse faire vos propres expériences. La prochaine fois, nous allons dépoussiérer quelques-unes de nos connaissances sur Page et créer une interface utilisateur graphique (GUI) qui facilitera les essais sur les données en utilisant un très puissant gadget personnalisé appelé « pandastable ». Jusque-là, amusez-vous bien et continuez à apprendre. |
| |
| |
Word_CDI: La forme du mot trouvée dans l'adaptation norvégienne de l'inventaire du développement de la communication de MacArthur-Bates | Word_CDI: La forme du mot trouvée dans l'adaptation norvégienne de l'inventaire du développement de la communication de MacArthur-Bates |
Translation: La traduction en anglais du mot norvégien | Translation: La traduction en anglais du mot norvégien |
AoA: L'age qu'a, en général, un enfant quand il apprend ce mot, en mois (estimation d'après l'inventaire du développement de la communication de MacArthur-Bates) | AoA: L'âge qu'a, en général, un enfant quand il apprend ce mot, en mois (estimation d'après l'inventaire du développement de la communication de MacArthur-Bates) |
VSoA: Nombre d'autres mots généralement connus d'un enfant quand il apprend ce mot (arrondi à la dizaine supérieure) | VSoA: Nombre d'autres mots généralement connus d'un enfant quand il apprend ce mot (arrondi à la dizaine supérieure) |
Lex_cat: La partie spécifique de la prononciation du mot | Lex_cat: La nature grammaticale précise du mot |
Broad_lex: La partie commune de la prononciation du mot | Broad_lex: La catégorie grammaticale du mot |
Freq: Mesure de la fréquence d'apparition de ce mot en norvégien | Freq: Mesure de la fréquence d'apparition de ce mot en norvégien |
CDS_freq: Mesure de la fréquence d'apparition de ce mot quand un adulte norvégien parle à un enfant norvégien | CDS_freq: Mesure de la fréquence d'apparition de ce mot quand un adulte norvégien parle à un enfant norvégien |
| |