Extraction d’un sous-ensemble de données avec la poc data#
Dans ce chapitre, nous verrons comment manipuler un ou plusieurs ensembles de données. Nous allons extraire un sous-ensemble de donné à partir d’une base de données provenant d’une bibliothèque temporaire ou permanente. Enfin, nous verrons comment fusionner deux tables ayant des noms de variables pareils ou différents ainsi que des formats pareils ou différents.
proc format;
    value $HF 'M'='Homme'
                'F'='Femme';
run;
proc print data=assu.cours_3 (firstobs = 1 obs = 5) noobs;
run;
| numeropol | type_prof | sexe | nbsin | cout_total | 
|---|---|---|---|---|
| 67942 | Technicien | Homme | 0 | . | 
| 52484 | Ingénieur | Homme | 0 | . | 
| 27817 | Ingénieur | Homme | 0 | . | 
| 32986 | Technicien | Femme | 4 | 15282.23 | 
| 45769 | Technicien | Homme | 0 | . | 
libname assu 'data';
Data assu.cours_3;
    set assu.eq_2;
    cout_total=sum(cout1,cout2, cout3, cout4, cout5, cout6, cout7);
    keep numeropol	type_prof	sexe nbsin cout_total; 
    format sexe HF.;
run;
proc print data=assu.cours_3 (firstobs = 1 obs = 5);
run;
| Obs | numeropol | type_prof | sexe | nbsin | cout_total | 
|---|---|---|---|---|---|
| 1 | 67942 | Technicien | Homme | 0 | . | 
| 2 | 52484 | Ingénieur | Homme | 0 | . | 
| 3 | 27817 | Ingénieur | Homme | 0 | . | 
| 4 | 32986 | Technicien | Femme | 4 | 15282.23 | 
| 5 | 45769 | Technicien | Homme | 0 | . | 
D’abord créons le format $HF où nous remplaçons le sexe M par Homme et le sexe F par Femme
Imaginons que nous voulons faire une étude sur les sinistres causés par les conducteurs masculins dans notre base de données. Nous voudrions alors séparer notre base de données en deux, et ce, selon le sexe de l’assuré.
data hommes;
    set assu.cours_3;
    where sexe = 'M';
run;
title "BD des hommes seulement";
proc print data=hommes (firstobs = 1 obs = 5) ;
run;
| Obs | numeropol | type_prof | sexe | nbsin | cout_total | 
|---|---|---|---|---|---|
| 1 | 67942 | Technicien | Homme | 0 | . | 
| 2 | 52484 | Ingénieur | Homme | 0 | . | 
| 3 | 27817 | Ingénieur | Homme | 0 | . | 
| 4 | 45769 | Technicien | Homme | 0 | . | 
| 5 | 60045 | Technicien | Homme | 0 | . | 
On voit bien que l’assurée du sexe féminin de la table cours_3 (la quatrième observation) est maintenant absente de la nouvelle table hommes
Remarquez qu’on aurait pu créer deux ensembles de données en un seul bloc de code. Une BD pour les hommes et une autre pour les femmes en utilisant la condition IF
data hommes femmes;
    set assu.cours_3;
        if sexe = 'F' then output femmes;
        else if sexe = 'M' then output hommes;
run;
title 'BD des femmes';
proc print data=femmes (firstobs = 1 obs = 5);
run;
title 'BD des hommes';
proc print data=hommes (firstobs = 1 obs = 5);
run;
title;
| Obs | numeropol | type_prof | sexe | nbsin | cout_total | 
|---|---|---|---|---|---|
| 1 | 32986 | Technicien | Femme | 4 | 15282.23 | 
| 2 | 22914 | Technicien | Femme | 0 | . | 
| 3 | 76422 | Infirmière | Femme | 0 | . | 
| 4 | 15847 | Technicien | Femme | 0 | . | 
| 5 | 42487 | Technicien | Femme | 1 | 165.98 | 
| Obs | numeropol | type_prof | sexe | nbsin | cout_total | 
|---|---|---|---|---|---|
| 1 | 67942 | Technicien | Homme | 0 | . | 
| 2 | 52484 | Ingénieur | Homme | 0 | . | 
| 3 | 27817 | Ingénieur | Homme | 0 | . | 
| 4 | 45769 | Technicien | Homme | 0 | . | 
| 5 | 60045 | Technicien | Homme | 0 | . | 
Avez-vous remarqué que nous appliquons un if sur la variable sexe ='M' et non ='Homme'?
Fusion des ensembles de données#
Maintenant que nous savons comment scinder une base de données, regardons comment nous pouvons les fusionner (ou les joindre).
data homme_femmes;
    set hommes femmes;
run;
title 'ensembles fusionnés, apperçu du début';
proc print data=homme_femmes (firstobs = 1 obs = 5);
run;
title 'ensembles fusionnés, apperçu de la fin de la bd';
proc print data=homme_femmes (firstobs = 28308 obs = 28313);
run;
title;
| Obs | numeropol | type_prof | sexe | nbsin | cout_total | 
|---|---|---|---|---|---|
| 1 | 67942 | Technicien | Homme | 0 | . | 
| 2 | 52484 | Ingénieur | Homme | 0 | . | 
| 3 | 27817 | Ingénieur | Homme | 0 | . | 
| 4 | 45769 | Technicien | Homme | 0 | . | 
| 5 | 60045 | Technicien | Homme | 0 | . | 
| Obs | numeropol | type_prof | sexe | nbsin | cout_total | 
|---|---|---|---|---|---|
| 28308 | 52 | Technicien | Femme | 0 | . | 
| 28309 | 89 | Informaticien | Femme | 3 | 33914.83 | 
| 28310 | 90 | Technicien | Femme | 0 | . | 
| 28311 | 1166 | Technicien | Femme | 0 | . | 
| 28312 | 4530 | Technicien | Femme | 1 | 38.48 | 
| 28313 | 9130 | Technicien | Femme | 0 | . | 
Imaginons maintenant que la variable numeropol de notre table des femmes_2 est plutôt nommée idPolice tel qu’illustré ci-dessous.
proc print data=assu.femmes_2 (firstobs = 1 obs = 5);
run;
| Obs | idPolice | type_prof | sexe | nbsin | cout_total | 
|---|---|---|---|---|---|
| 1 | 32986 | Technicien | Femme | 4 | 15282.23 | 
| 2 | 22914 | Technicien | Femme | 0 | . | 
| 3 | 76422 | Infirmière | Femme | 0 | . | 
| 4 | 15847 | Technicien | Femme | 0 | . | 
| 5 | 42487 | Technicien | Femme | 1 | 165.98 | 
Et nous voulons fusionner la table d’hommes avec celle des femmes_2 afin d’avoir qu’une seule table. Nous avons deux choix,
- Renommer la variable - numeropolpar- idPolicedans la table des hommes.
- ou renommer la variable - idPolicepar- numeropoldans la table des femmes_2
En utilisant merge qui nécessite de faire un tri d’abord.
/* on applique d'abord le sort */
proc sort data=hommes;
    by numeropol;
run;
proc sort data=assu.femmes_2;
    by idPolice;
run;
/* Ensuite on fusionne */
data merge_hommes_et_femmmes_2;
    merge hommes
    assu.femmes_2(rename=(idPolice = numeropol));
    by numeropol;
run;
/* Enfin un apperçu dy résultat */
proc print data=merge_hommes_et_femmmes_2 (firstobs = 1 obs = 5);
run;
proc print data=merge_hommes_et_femmmes_2 (firstobs = 28161 obs = 28166);
run;
| Obs | numeropol | type_prof | sexe | nbsin | cout_total | 
|---|---|---|---|---|---|
| 1 | 46 | Technicien | Homme | 1 | 856.248 | 
| 2 | 46 | Technicien | Homme | 0 | . | 
| 3 | 52 | Technicien | Femme | 0 | . | 
| 4 | 52 | Technicien | Femme | 0 | . | 
| 5 | 63 | Technicien | Homme | 0 | . | 
| Obs | numeropol | type_prof | sexe | nbsin | cout_total | 
|---|---|---|---|---|---|
| 28161 | 88997 | Infirmière | Femme | 0 | . | 
| 28162 | 88998 | Technicien | Femme | 0 | . | 
| 28163 | 89003 | Technicien | Femme | 0 | . | 
| 28164 | 89011 | Infirmière | Homme | 0 | . | 
| 28165 | 89028 | Infirmière | Homme | 0 | . | 
| 28166 | 89033 | Technicien | Femme | 0 | . | 
Il arrive des fois que les noms de variable sont les mêmes, mais que le format de ces dernières est différent d’une table à une autre qu’on veuille fusionner. Regardons un exemple pour mieux comprendre.
Soit la petite table NAS_1 qui contient des numéros d’assurance sociale au format 123456789
data NAS_1;
    input SS: 9.
        DOB:  MMDDYY10. 
        Gender : $1.;
    FORMAT DOB  MMDDYY10.;
    DATALINES;
    332211009 11/14/1993 M
    123456789 05/17/1983 F
    987789321 04/01/1991 F
    ;
proc print data=NAS_1;
run; 
| Obs | SS | DOB | Gender | 
|---|---|---|---|
| 1 | 332211009 | 11/14/1993 | M | 
| 2 | 123456789 | 05/17/1983 | F | 
| 3 | 987789321 | 04/01/1991 | F | 
soit la table NAS_2 qui contient d’autres informations sur les individus de la table NAS_1 mais que cette fois, le format de la variable SS est 123-45-6789
data NAS_2;
    input SS: $11.
        JobCode:  $13. 
        Salary : 9.;
    DATALINES;
    332-21-1009 A10 45123
    123-45-6789 B5 35400
    987-78-9321 A20 87900
    ;    
proc print data=NAS_2 noobs;
run;
| SS | JobCode | Salary | 
|---|---|---|
| 332-21-1009 | A10 | 45123 | 
| 123-45-6789 | B5 | 35400 | 
| 987-78-9321 | A20 | 87900 | 
Nous créons une nouvelle table appelée NAS_1B qui est une réplique de la table NAS_1 dans laquelle nous changeons le format de la variable SS sous le même format que la table NAS_2
data NAS_1B;
    set NAS_1(rename=(SS = NumSS));
    SS = put(NumSS,ssn11.); /*ssn c'est un formt de NAS*/
    drop NumSS;
run;
/* on applique d'abord le sort */
proc sort data=NAS_1B;
    by SS;
run;
proc sort data=NAS_2;
    by SS;
run;
/* Ensuite on fusionne */
data les_deux_NAS;
    merge NAS_1B NAS_2;
    by SS;
run;
title 'NAS_1';
proc print data=NAS_1 noobs;
run;
title 'NAS_1B';
proc print data=NAS_1B noobs;
run;
title 'NAS_2';
proc print data=NAS_2 noobs;
run;
title 'les_deux_NAS';
proc print data=les_deux_NAS noobs;
run;
title;
| SS | DOB | Gender | 
|---|---|---|
| 332211009 | 11/14/1993 | M | 
| 123456789 | 05/17/1983 | F | 
| 987789321 | 04/01/1991 | F | 
| DOB | Gender | SS | 
|---|---|---|
| 05/17/1983 | F | 123-45-6789 | 
| 11/14/1993 | M | 332-21-1009 | 
| 04/01/1991 | F | 987-78-9321 | 
| SS | JobCode | Salary | 
|---|---|---|
| 123-45-6789 | B5 | 35400 | 
| 332-21-1009 | A10 | 45123 | 
| 987-78-9321 | A20 | 87900 | 
| DOB | Gender | SS | JobCode | Salary | 
|---|---|---|---|---|
| 05/17/1983 | F | 123-45-6789 | B5 | 35400 | 
| 11/14/1993 | M | 332-21-1009 | A10 | 45123 | 
| 04/01/1991 | F | 987-78-9321 | A20 | 87900 | 
Dans le prochain cours, nous verrons qu’il est beaucoup plus simple d’appliquer ces concepts en utilisant la procédure PROC sql qui ne nécessite pas de tri préalable comme la fonction merge que nous venons de voir.
Données manquantes#
Lorsqu’une valeur de donnée est inconnue, alors nous avons une donnée manquante. Une donnée manquante est une donnée valide, elle est affichée par un espace (vide) dans une variable (colonne) de type caractère, et par un point lorsqu’il s’agit d’une variable (colonne) numérique.
Nommer des variables dans SAS#
SAS possède une convention afin de donner des noms de variables. Nous pouvons nommer nos variables avec une combinaison de 1 à 32 caractères, numériques, underscore ou une combinaison de ces trois derniers. Les lettres peuvent être en minuscule ou majuscule.
