SAS9

Automatizar el procesamiento de mltiples tablas en una carpeta

Simon 10 vues

Un desafo frecuente para los analistas de SAS© es tener que repetir una operacin (como un MERGE para aadir una columna) en decenas de tablas situadas en el mismo directorio. Escribir 50 veces la llamada a la macro %jig(name=AB);, %jig(name=AC);... es tedioso y fuente de errores.

Cmo hacer que SAS© "escanee" la carpeta y aplique la macro automticamente a cada archivo? Aqu est el mtodo elegante propuesto por WeAreCas, utilizando los metadatos de SAS©.

1. La Estrategia: Diccionarios y CALL EXECUTE

El enfoque se basa en dos pilares de la programacin dinmica SAS©:

  1. Recuperar la lista de nombres: Utilizar las vistas de diccionario (SASHELP.VTABLE) para listar automticamente todo lo que se encuentra en una biblioteca.

  2. Generar el cdigo dinmicamente: Utilizar la instruccin CALL EXECUTE en un Paso de Datos para lanzar la macro para cada nombre encontrado.

2. El Cdigo Paso a Paso

Paso 0: Definir la Macro de procesamiento

Este es el cdigo que el usuario quiere ejecutar para una sola tabla.

1%macro jig(name);
2 DATA datdir.NEW_&name;
3 /* Attention : les deux tables doivent être triées par ID au préalable */
4 MERGE excelsheetdata datdir.&name;
5 BY ID;
6 RUN;
7%mend jig;

Paso 1: Listar las tablas objetivo (PROC SQL)

En lugar de escribir los nombres a mano, le preguntamos a SAS©: "Dame la lista de todas las tablas no vacas presentes en la biblioteca 'DATDIR'."

1PROC SQL;
2 create TABLE liste_tables as
3 select memname
4 from sashelp.vtable
5 where LIBNAME='DATDIR' /* Nom de la lib en MAJUSCULES */
6 and memname like 'DATA_%'; /* Filtre optionnel si besoin */
7QUIT;
Nota: SASHELP.VTABLE contiene los metadatos de todas las tablas activas (nombre, nmero de observaciones, fecha de creacin, etc.).

Paso 2: La automatizacin (CALL EXECUTE)

Aqu es donde ocurre la magia. Recorremos la lista creada en el paso 1, y para cada fila, construimos un comando de texto que llama a la macro.

1DATA _null_;
2 SET liste_tables;
3
4 /* Construction de la chaîne : '%jig(TABLE_1)' */
5 /* On utilise STRIP pour enlever les espaces inutiles du nom */
6 commande = '%jig(' || strip(memname) || ')';
7
8 /* Exécution immédiate de cette commande */
9 call execute(commande);
10RUN;

3. Anlisis de la sintaxis CALL EXECUTE

En la solucin propuesta por WeAreCas, notars una sintaxis un poco compleja:

call execute( '%nrstr( %%)' !! 'jig(' !! memname !! ') ' );

Por qu %nrstr(%%)?

  • CALL EXECUTE resuelve las macros durante la ejecucin del Paso de Datos.

  • A veces, se desea retrasar esta ejecucin o proteger ciertos caracteres especiales.

  • En la mayora de los casos simples (como aqu), call execute('%jig(' || memname || ')'); suele ser suficiente.

  • La adicin de %nrstr sirve para "ocultar" el signo % para evitar que SAS© intente resolver la macro demasiado pronto o si hay conflictos de tiempo.

Resumen del Mtodo

MtodoVentajaInconveniente
ManualSimple de entender.Largo, repetitivo, riesgo de olvido.
Comodines (ej: DATA_: )Rpido para un SET simple (apilamiento).No funciona para un MERGE complejo (unin).
Diccionarios + Call ExecuteCompletamente automtico, flexible.Requiere conocer SQL y la meta-programacin.

No olvide que para que un MERGE funcione, todas sus tablas (las 50!) deben estar previamente ordenadas por la variable clave (ID). Si no es as, deber aadir un PROC SORT dentro de su macro %jig antes del paso de Datos.