length ifn funcion findw merge sas

merge - ifn - retain sas



¿Es posible fusionar más de dos conjuntos de datos en un paso de datos SAS con diferentes claves? (2)

Esto es bastante trivial en (PROC) SQL, pero mirando hacerlo con un paso de datos, y estoy encontrando una seria falta de documentación sobre el tema.

La mayoría de las combinaciones de conjuntos de datos múltiples tienen las mismas claves que se utilizan en la instrucción BY.


Técnicamente, es posible hacer esto incluso usando la declaración de merge , que probablemente sorprenderá a la mayoría. Algunas veces incluso obtienes lo que esperas en términos de datos.

Esto funciona como se esperaba:

proc means data=sashelp.class; class age; types age; var height; output out=mean_height_age mean= /autoname; run; proc means data=sashelp.class; class age sex; types age*sex; var weight; output out=mean_weight_sex mean= /autoname; run; proc sort data=sashelp.class out=class; by age sex; run; data class_means; merge class mean_height_age; by age; merge class mean_weight_sex; by age sex; run;

Estos funcionan porque el orden no es incongruente (el segundo by es compatible con el primero by ).

Sin embargo, si está pensando más en una clase de base de datos relacional en la que tiene claves de combinación totalmente separadas, es posible engañar a SAS para que haga algo que parece funcionar, pero no es así. Tenga en cuenta que el conjunto de datos final parece estar algo mezclado cuando se trata de edades, es porque las filas entrantes en la segunda declaración de fusión de class_index sobrescriben el primer conjunto de registros y vienen en un orden diferente (según el índice).

proc means data=sashelp.class; class age; types age; var height; output out=mean_height_age mean= /autoname; run; proc means data=sashelp.class; class sex; types sex; var weight; output out=mean_weight_sex mean= /autoname; run; data class_index(index=(sex) index=(age)); set class; run; data class_means; merge class_index mean_height_age; by age; merge class_index mean_weight_sex; by sex; run;

Puede ver esto claramente al volver a establecer el conjunto de datos class_index .

data class_means; merge class_index mean_height_age; by age; merge class_index mean_weight_sex; by sex; set class_index; by age; run;

Volver a corregir por edad, pero incorrecto por sexo.

Si vas a hacer eso (dos claves separadas y no relacionadas), tienes muchas opciones. El más comúnmente utilizado es probablemente un formato definido por el usuario. Esto usa la tabla de búsqueda de formato para almacenar la relación, y luego simplemente put (o input si quiere un número, pero puede que tenga que input(put( si debe hacer un formato y no una información).

data for_fmt_age; set mean_height_age; start = age; label = height_mean; fmtname=''HEIGHTAGEF''; output; run; data for_fmt_sex; set mean_weight_sex; start = sex; label = weight_mean; fmtname=''$WEIGHTSEXF''; output; run; proc format cntlin=for_fmt_sex; quit; proc format cntlin=for_fmt_age; quit; data want; set sashelp.class; mean_height = put(age,heightagef.); mean_weight = put(sex,$weightsexf.); run;

Una segunda opción es el conjunto con clave; eso es más similar a una fusión, y solo requiere que se cree un índice en el conjunto de datos combinado.

proc datasets lib=work; modify mean_height_age; index create age; run; modify mean_weight_sex; index create sex; run; quit; data class_nomerge; set class_index; set mean_height_age key=age; set mean_weight_sex key=sex; run;

Finalmente, podría usar tablas hash, un poco más esotéricas pero realmente muy fáciles de usar. No se requiere clasificación ni nada más, solo el paso de datos en sí.

data want; set sashelp.class; if 0 then set mean_height_Age mean_weight_sex; if _n_=1 then do; declare hash h_age(dataset:''mean_height_age''); h_age.defineKey(''age''); h_age.defineData(''height_mean''); h_age.defineDone(); declare hash h_sex(dataset:''mean_weight_sex''); h_sex.defineKey(''sex''); h_sex.defineData(''weight_mean''); h_sex.defineDone(); end; rc_age = h_age.find(); rc_sex = h_sex.find(); run;


Una búsqueda de sas 9.4 "combining SAS data sets: methods" debería profundizar en la documentación.

Paso de datos El proceso MERGE / BY requiere que todas las fuentes de datos entrantes tengan los mismos nombres y tipos de columnas.

Los datos entrantes se pueden ajustar superficialmente usando RENAME = () para hacer que los nombres de columna se alineen con las columnas enumeradas en la instrucción BY. Si las longitudes de datos de caracteres no coinciden existe la posibilidad de truncamiento y coincidencias falsas.

Para el caso en que sean necesarias transformaciones más complicadas (por ejemplo, identificación numérica en db remoto e identificación de caracteres en el conjunto de datos local) para realizar una fusión, puede hacerlo utilizando vistas de SQL para la transformación + orden de preprocesamiento. Esto es muy útil para el caso de hacer un procesamiento basado en matrices a través de una fila que es onerosa o difícil en construcciones de SQL.

La comprensión de Program Data Vector y de cómo el compilador DATA Step la construye en base a las variables en orden de introducción a través de las sentencias length, attrib, SET y MERGE es esencial para una MERGE compleja.