Posts Tagged ‘group’

h1

Une option SAS 9.2 pour ODS PDF : répéter une valeur groupée sur plusieurs pages

août 3, 2010

Lorsque vous construisez un listing avec ODS PDF et PROC REPORT l’option GROUP de l’instruction DEFINE sert à n’afficher chaque valeur de la variable concernée qu’une seule fois.

Hors, si cette valeur s’applique aux observations de plusieurs pages, elle ne sera pas répétée à moins d’ajouter l’option SPANROWS nouvelle avec SAS 9.2.

Cette options ne fonctionne pas actuellement avec ODS RTF.

Voici un exemple pour tester par vous même.

1. Le setting

Par simple soucis de présentation, quelques instructions de paramétrage sont données.

  • Enlever le titre par défaut avec l’instruction TITLE.
  • Enlever la date et le numéro de page par défaut et alignez le résultat à gauche.
  • Créer un format caractère SEX où M réfère à Garçon et F à Fille.


*——————————————–;
* Setting;
*——————————————–;

title;
options nodate nonumber nocenter;

proc format;
value $ sex ‘M’=‘Garçon’
‘F’=‘Fille’;
run;

2. Préparation des données

Afin d’avoir assez de données le fichier CLASS est multiplié par 5. Les noms sauvegardés dans la variable NAME sont incrémentés d’un nombre.

*——————————————–;
* 2. Data Preparation;
*——————————————–;

data class;
set sashelp.class;
output;
name=cats(name,’1′);
output;
name=cats(name,’2′);
output;
name=cats(name,’3′);
output;
name=cats(name,’4′);
output;
name=cats(name,’5′);
output;
run;

3. Reporting

Enfin la section qui nous intéresse vraiment : générer un fichier .RTF et un fichier .PDF avec l’option SPANROWS et voir que que seul ODS RTF tient compte de cette option pour répéter l’observation en début de chaque nouvelle page.


*——————————————–;
* 3. Reporting;
*——————————————–;

ods listing close;
ods rtf file=‘C:\sasref\test1.rtf’;
ods pdf file=‘C:\sasref\test1.pdf’;


proc report data=class spanrows nowd;
column sex name;
define sex / group ‘Sexe’;
define name / display ‘Nom’ ;
run;


ods pdf close;
ods rtf close;
ods listing;

h1

6 notions pour débuter avec PROC REPORT

mars 26, 2008

Feu 

Pour créer un tableau et le publier, la procédure REPORT est disponible. Je vous propose de voir sa structure de base.

1. Lister vos variables avec l’instruction COLUMN : la procédure REPORT doit contenir au minimum une instruction COLUMN listant les variables à publier dans l’ordre d’apparition souhaité.

Pour les utilisateurs de SAS pour Windows, on ajoutera l’option NOWD dans l’instruction PROC REPORT, pour éviter l’ouverture d’une fenêtre indépendante.

2 Personnalisez les colonnes : par défaut, les colonnes auront pour nom celui de la variable. Pour les personnalisez, on ajoute une instruction DEFINE par colonne.

proc report data=result_pat nowd;
   column pays pays_txt patient_id cnt pct;
   define pays       / display ‘ ‘;
   define pays_txt   / display ‘Pays’;
   define patient_id / display ‘ID’;
   define cnt        / display ‘N’;
   define pct        / display ‘%’;
run;

3. Privilégiez l’affiche en mode DISPLAY : par défaut les variables textes seront en mode DISPLAY tandis que les variables numériques seront en mode ANALYSIS. En d’autres termes, SAS peut potentiellement regrouper et additionner des valeurs numériques. Je pense notamment lorsqu’on utilise l’option GROUP sur d’autres variables. De plus, les valeurs textes seront alignées à gauche et les valeurs numériques seront alignées à droite.

Mon choix est donc de convertir toutes mes variables à afficher en texte avant et de n’utiliser PROC REPORT que comme un outil de publication. Vous pouvez, de plus, explicitement indiquer le mode DISPLAY dans les instructions DEFINE.

4. Trier les données et ne pas afficher certaines colonnes : en plus des affichages par défaut DISPLAY et ANALYSIS, vous avez l’affichage ORDER. Il est vivement conseillé de noter explicitement l’option ORDER= (formated, data, freq ou internal) car la valeur par défaut risque d’évoluer dans les prochaines versions de SAS. On peut également utiliser le mot-clé DESCENDING pour un tri par ordre décroissant.

Il est souvent plus facile de trier les données si elles sont numériques. Par exemple, imaginez que vous vouliez trier vos données par pays avec en premier des pays d’Europe par ordre alphabétique (Allemagne, France, Royaume-Uni) puis des pays d’Asie par ordre alphabétique (Indonésie, Malaisie, Singapour, Thaïlande). Vous pouvez créer un format numérique avec des valeurs allant de 1 à 7 (1 pour Allemagne, 7 pour Thaïlande).

Pour être cohérent avec mon propos précédent, je vous conseille d’avoir deux variables :

  • d’un côté la variable numérique qui sert pour le tri mais que ne sera pas affichées. Pour cela, il y a l’option NOPRINT de l’instruction DEFINE ;
  • et de l’autre, la variable texte créée préalablement à partir de la variable numérique et du format avec une fonction PUT.

5. Grouper les données et créer des breaks : imaginez que vous ayez plusieurs patients du même pays. Vous aurez autant de fois le nom de pays qu’il y a de patients. Pour alléger le tableau, vous pouvez n’afficher le pays que la première fois. Au lieu de DISPLAY, ANALYSIS, ORDER, etc. vous utilisez alors l’option GROUP dans l’instruction DEFINE.

Notez que toutes les colonnes à gauche devront donc être également groupées.

Il est possible d’utiliser ORDER=… avec GROUP comme pour l’option ORDER.

Un des avantages de GROUP est de définir entre les groupes des séparations. Pour cela, il y l’instruction BREAK AFTER appelle la variable groupée en question. Le type de séparation est défini par l’option. SKIP par exemple permet de sauter une ligne entre les groupes. Mais cette instruction ne fonctionne pas avec ODS RTF. Il faut alors utiliser la syntaxe COMPUTE/ENDCOMP.

proc report data=result_pat nowd;
   column pays pays_txt patient_id cnt pct;
   define pays       / group order=data noprint;
   define pays_txt   / group ‘Pays’;
   define patient_id / display ‘ID’;
   define cnt        / display ‘N’;
   define pct        / display ‘%’;
   *break after pays / skip;
   compute before;
      line ‘ ‘;
   endcomp;
   compute after pays_num;
      line ‘ ‘;
   endcomp;
run;

6. Les faiblesses de l’instruction ACROSS : imaginez que vous ayez les fréquences et pourcentages pour deux drogues. Cela vous donne 4 colonnes dans votre tableau finale. Mais, dans votre tableau d’origine, vous avez 3 colonnes : le type de drogue, les fréquences et les pourcentages. L’instruction ACROSS permet de « transposer » l’information. Mais si, en plus, vous voulez rajouter une colonne à droite, vous rencontrerez de réelles difficultés.

Comme précédemment, je choisi d’agencer mes données comme il me convient avant la procédure. Je n’utilise PROC REPORT que pour l’affichage. Cela implique souvent l’usage d’un PROC TRANSPOSE et d’un MERGE (where=() rename=()).

proc sort data=result_drug;
   by pays;
run;

proc transpose data   = result_drug
               out    = result_drug_across
               prefix = drug_;
   by pays;
   var cnt pct;
   id drug;
run;

data result_drug_across (drop=_NAME_);
   merge result_drug_across
          (where=(lowcase(_name_)=‘cnt’)
           rename=(drug_1=cnt_1 drug_2=cnt2))
         result_drug_across
          (where=(lowcase(_name_)=‘pct’)
           rename=(drug_1=pct_1 drug_2=pct2));
   by pays;
run;

Pour une information plus détaillées sur DISPLAY, ANALYSIS, GROUP, ORDER, ACROSS vous trouverez la page « Concept: REPORT procedure ». Notez que je n’ai pas parlé de COMPUTED, dans la même veine que GROUP, DISPLAY, ACROSS, ANALYSIS, mais que celle-ci permet de faire des calculs simples (sommation, etc).

Conclusion

En conclusion, la procédure REPORT est un outil qui, certes très puissant, peut vite devenir très compliqué. De mon expérience, il apparaît plus judicieux de restreindre l’usage de PROC REPORT à la diffusion de résultats préalablement agencés en triant les données avec des variables numériques non affichées et ne montrant que les variables textes.

Pour plus de détails sur la procédure REPORT, vous pouvez consulter le prochain article intitulé « 6 subtilités de PROC REPORT » et le chapitre PROC REPORT de la documentation en ligne.

Annexe:

data result_pat;
   length pays_txt $10;
   input pays pays_txt $ patient_id cnt pct;
   datalines;
1 Maroc      1 10  20
1 Maroc      2 25  50
1 Maroc      3 15  30
2 Luxembourg 1 18  36
2 Luxembourg 2 32  64
3 Canada     1  5 100
;
run;

data result_drug;
   input pays drug cnt pct;
   datalines;
1 1 10 20
2 1 18 36
1 2 40 80
2 2 32 64
3 1 5 100
;
run;