JSL: encuentre el porcentaje de datos faltantesTengo una tabla de datos con 3 columnas.

Necesito crear una tabla que muestre el porcentaje de datos faltantes en la columna ALTURA agrupados por ID y SUB_ID. En el caso anterior el resultado debería ser:

Pero es posible en algunos casos que no haya filas con datos faltantes. En ese caso, el porcentaje faltante debería ser 0.

Necesito ayuda para escribir un script JSL para esto. Agradeceré cualquier orientación. Tengo tres problemas en mi script a continuación:
1. ¿Cómo puedo realizar un seguimiento del identificador/referencia a una tabla de datos para poder recuperarla en cualquier momento? Siempre he usado "dt = CurrentDataTable" al comienzo del script. Pero después de haber creado algunas tablas de resumen/tablas de subconjunto, pierdo la referencia a la tabla original y no sé cómo actualizarla.
2. Necesito que esto funcione incluso cuando no faltan filas. En este momento el guión simplemente se detiene en el medio.
3. Necesito que se cierren todas las mesas excepto la mesa final con el porcentaje faltante.
// Read the original table
dt = CurrentDataTable();
main_table = Data Table( dt ) << get name; // get the table name
// Create a summary table with no of rows grouped by ID and SUB_ID
dt_summary = dt<< Summary(Group(:ID, :SUB_ID), Freq("None"), Weight("None"), output table name( "Main Table Summary"));
:N Rows << Set Name( "Total No of Rows" );
// Create a subset of the original table with only the missing rows
Current Data Table(Data Table(main_table));
dt = CurrentDataTable();
dt_missing = dt << select where( Is Missing( :HEIGHT ) == 1 ) << Subset(Output Table Name("Missing Rows"));
If( !Is Empty( dt_missing ),
dt_missing_summary = Data Table( dt_missing ) << Summary(
Group( :ID, :SUB_ID ),Freq("None"), Weight("None"), output table name( "Missing Rows Table Summary"));
:N Rows << Set Name( "No of Rows with Missing Data" );
dt_missing_summary << Update(
With( Data Table( dt_summary ) ),
Match Columns( :ID = ID, :SUB_ID = :SUB_ID ),
Add Columns from Update table( :Total No of Rows )
);
New Column( "PercentMissing",
Numeric,
"Continuous",
Format( "Percent", 12, 2 ),
Formula( :No of Rows with Missing Data / :Total No of Rows )
);
);
//Close( dt_missing, nosave );
//Close( dt_summary, nosave );Gracias
Combinación y limpieza de datosRe: JSL - Buscar % de datos faltantesGracias por la respuesta. Hasta ahora no sabía que N Missing podría usarse para encontrar las filas de datos que faltan. Facilitó mucho el trabajo y redujo algunos pasos del guión.Re: JSL - Buscar % de datos faltantesGracias por la explicación paso a paso. Los pasos 1, 2 y 4 son los nuevos trucos que aprendí y son muy útiles. No es de extrañar por qué mi script fallaba si no faltaban datos. Recordaré dividir la declaración cuando aplique múltiples condiciones.Re: JSL - Buscar % de datos faltantesGracias por la solución simple y compacta. Agrega una columna adicional a la tabla original, pero eso no es un problema para mí.Re: JSL - Buscar % de datos faltantesPOR FAVOR VUELVA A LEER si vio esto antes. Hubo un error.
El uso de la función integrada de JMP, Col N Missing (), simplifica esta tarea. Mostraré 2 enfoques.
SOLUCIÓN #1:
- Cree una columna para contar los desaparecidos por grupo en la primera tabla.
- Resume la primera tabla.
- Cambie el nombre de la columna N filas (si lo desea) y cree una columna de fórmula para la proporción.
Names Default To Here( 1 );
//these 2 lines just create a table with overall missing rate of 35% for the weight varable.
dt = Open( "$Sample_Data\Car Physical Data.jmp" );
dt:weight[Loc( J( 116, 1, Random Binomial( 1, .35 ) ) == 0 )] = .;
//add a formula column to compute n missing rows.
dt << New Column( "Missing Rows", formula( Col N Missing( :weight, :country, :type ) ) );
//create summary table, rename N Rows column, and add a % missing formula column.
dtSum = dt << Summary( Group( :Country, :Type, :missing rows));
dtSum:N Rows << set name("Total Rows");
dtSum << new column ("Pct Missing", formula(:missing rows / :total rows));
SOLUCIÓN #2:
- Cree todas las columnas de fórmula en la primera tabla y luego realice un resumen directo.
- Opcionalmente, elimine la columna N filas de la tabla Resumen.
** El "te pillé" en este método está en la función Total de filas ( ). Debe comenzar con un "1" para el primer argumento, para que sirva como columna ficticia, porque el primer argumento no se puede utilizar como columna de agrupación. Omita el 1 y verá que los recuentos reflejan únicamente el número de filas en el grupo "tipo"... no la combinación de país y tipo.
Saludos y disculpas por el error la primera vez.
Names Default To Here( 1 );
//don't worry about these; these are just to get a table present with some missing values @ an
//overall missing rate of 35%
dt = Open( "$Sample_Data\Car Physical Data.jmp" );
dt:weight[Loc( J( 116, 1, Random Binomial( 1, .35 ) ) == 0 )] = .;
//create formula columns using built-in functions to get what you're after.
dt << New Column( "Missing Rows", formula( Col N Missing( :weight, :country, :type ) ) );
dt << New Column( "Total Rows", formula( Col Number( 1, :country, :type ) ) );
dt << New Column( "Group Pct Missing", formula( :missing rows / :total rows ) );
//view summary table.
dtSum = dt << Summary( Group( :Country, :Type, :missing rows, :total rows, :group pct missing));
Re: JSL - Buscar % de datos faltantes- Necesitas agregar
Names Default To Here( 1 );
para limitar las variables especificadas en su secuencia de comandos para que no sean cambiadas por variables en otras secuencias de comandos con el mismo nombre, cambiando los valores en su secuencia de comandos actual
- Parece que tiene un malentendido acerca de la función Tabla de datos actuales().Se puede utilizar de 2 maneras diferentes y le ayudará a no perder la referencia a su tabla de datos original.La especificación
dt = Current Data Table();
has estado usando correctamente.Y cuando más adelante en su secuencia de comandos desee convertir la tabla de datos original en la "tabla de datos actual", todo lo que tiene que hacer escurrent data table(dt);
Esto le indicará a JMP que utilice "dt" como tabla de datos actual.Lo que debes abstenerte de hacer es reasignar "dt" colocándolo en el lado izquierdo de un "=".
- A veces no es bueno combinar acciones en una sola afirmación.Su
dt_missing = dt << select where( Is Missing( :HEIGHT ) == 1 ) << Subset(Output Table Name("Missing Rows"));espera seleccionar filas y subconjuntos de la tabla, todo en una sola declaración.El problema es que no podrá brindarle lo que desea si no faltan valores de :Height.En mi reelaboración de su script (a continuación), la tabla de datos dt tiene las filas seleccionadas o no, y luego se realiza la verificación para ver si se han encontrado filas faltantes y, de ser así, y solo entonces, continuar con el procesamiento.dt << select where( Is Missing( :HEIGHT ) == 1 );
If( N Rows( dt << get selected rows ) > 0,
- La función Try() es muy útil para ejecutar funciones que posiblemente podrían fallar y, si lo hacen, no querrás que el script deje de ejecutarse.Las funciones Close() que estás usando y excelentes para usar la función Try()
Try( Close( dt_missing, nosave ) );
Try( Close( dt_summary, nosave ) );
Espero que esto sea útil... si tiene más preguntas, por favor responda.
Names Default To Here( 1 );
// Read the original table
dt = Current Data Table();
//main_table = Data Table( dt ) << get name; // get the table name
// Create a summary table with no of rows grouped by ID and SUB_ID
dt_summary = dt << Summary(
Group( :ID, :SUB_ID ),
Freq( "None" ),
Weight( "None" ),
output table name( "Main Table Summary" )
);
:N Rows << Set Name( "Total No of Rows" );
// Create a subset of the original table with only the missing rows
//Current Data Table(Data Table(main_table));
//dt = CurrentDataTable();
dt << select where( Is Missing( :HEIGHT ) == 1 );
If( N Rows( dt << get selected rows ) > 0,
dt_missing = dt << Subset( Output Table Name( "Missing Rows" ), selected rows( 1 ) );
dt_missing_summary = Data Table( dt_missing ) <<
Summary(
Group( :ID, :SUB_ID ),
Freq( "None" ),
Weight( "None" ),
output table name( "Missing Rows Table Summary" )
);
:N Rows << Set Name( "No of Rows with Missing Data" );
dt_missing_summary << Update(
With( Data Table( dt_summary ) ),
Match Columns( :ID = ID, :SUB_ID = :SUB_ID ),
Add Columns from Update table( :Total No of Rows )
);
New Column( "PercentMissing",
Numeric,
"Continuous",
Format( "Percent", 12, 2 ),
Formula( :No of Rows with Missing Data / :Total No of Rows )
);
);
Try( Close( dt_missing, nosave ) );
Try( Close( dt_summary, nosave ) );
Re: JSL - Buscar % de datos faltantes@jthi ,
Estábamos pensando en lo mismo al mismo tiempo, me gusta que tu respuesta sea un poco más completa que la mía y estoy de acuerdo con las sugerencias de los puntos 1 y 3.
Re: JSL - Buscar % de datos faltantesPrimero, recomiendo encarecidamente consultar la guía de secuencias de comandos JMP: Guía de secuencias de comandos JMP15 y el índice de secuencias de comandos que se encuentra en Jmp / Ayuda / Índice de secuencias de comandos. Estas son muy buenas fuentes para secuencias de comandos JSL.
Para realizar esta tarea no necesitarás ningún jsl:
1. Comencemos con la tabla de ejemplo que nos proporcionó con dos valores faltantes.
2. Cree un resumen de la tabla con N faltantes con altura como estadísticas y SUB_ID e ID como grupo.


3. Cree una nueva fórmula seleccionando N filas y N columnas faltantes (ALTURA)

4. Cambie el formato a Porcentaje en Propiedades de columna y cambie el nombre de las columnas según sea necesario
Según estos pasos, también podría utilizar con bastante facilidad la funcionalidad proporcionada por JMP para mostrar los scripts necesarios para los pasos a seguir para cambiar este proceso manual a un proceso automatizado (se deben realizar pequeños cambios para hacerlo más sólido).
Y para tus preguntas 1 y 3:
1. Depende mucho de cómo cree/abra/obtenga sus tablas de datos. Si siempre tiene el mismo nombre, puede hacer referencia a eso, pero no confiaría en eso a largo plazo, ya que es muy fácil crear múltiples tablas de datos con el mismo nombre y JMP agregará indexación después de los nombres. Pero se puede hacer referencia a estos mediante Datatable (nombre de tabla de datos).
3. Puede obtener una lista de tablas de datos con Obtener lista de tablas de datos(). Recorra las tablas de datos y cierre las innecesarias. Pero en mi opinión, siempre debes cerrar la tabla de datos que no necesitarás tan pronto como sea posible con Cerrar (referencia a la tabla de datos, sin guardar).
Script de ejemplo para realizar la tarea:
Names Default To Here(1);
//create example data and add reference to dt variable
dt = New Table("exampledata",
Add Rows(8),
Compress File When Saved(1),
New Column("ID",
Numeric,
"Nominal",
Format("Best", 12),
Set Values([1, 1, 1, 1, 2, 2, 2, 2])
),
New Column("SUB_ID",
Character,
"Nominal",
Set Values({"A", "A", "B", "B", "A", "A", "B", "B"})
),
New Column("HEIGHT",
Numeric,
"Continuous",
Format("Best", 12),
Set Values([10, 11, ., 9, ., 12, 8, 12])
)
);
//note Link to original data table(0)
//dt_summary is reference to the new Summary table
dt_summary = dt << Summary(
Group(:ID, :SUB_ID),
N Missing(:HEIGHT),
Freq("None"),
Weight("None"),
Link to original data table(0),
output table name("Main Table Summary")
);
//close unnecessary datatable
Close(dt, no save);
//add new column with formula
dt_summary << New Column("Percent Missing",
Numeric,
"Continuous",
Format("Percent", 12, 0),
Formula(:Name("N Missing(HEIGHT)") / :"N Rows"),
);
//rename columns
Column(dt_summary, "N Rows") << Set Name("Total No of Rows");
Column(dt_summary, "N Missing(HEIGHT)") << Set Name("No of Rows with Missing Data");
Re: JSL - Buscar % de datos faltantesHola @rverma ,
Veo que puedes aprovechar el resumen dentro de las tablas.Puedo producir la mayor parte de lo que estás haciendo en esa sección y luego agregar una columna con una fórmula para calcular la proporción (%).
Podría hacer el script como este, que seguirá funcionando si no faltan datos (agrega el elemento 2):
sumdt = dt << Summary( Group( :ID, :SUB_ID ), N Missing( :HEIGHT ), Freq( "None" ), Weight( "None" ) );
sumdt << New Column( "Percent Missing",
Numeric,
Continuous,
Format( Percent ),
Formula( :"N Missing(HEIGHT)"n / :N Rows )
);
Entonces podrías subconjunto de esto. Y aún cierre las otras ventanas.
Es un comienzo