referencia de columna robustaDespués de unos minutos de codificación con JSL, los usuarios se preguntan acerca de objetos extraños como :sexo en
dt = Open( "$SAMPLE_DATA/Big Class.jmp" );
x = :sex
Los usuarios expertos tienen cierta experiencia con dichas referencias de columnas y las utilizan todo el tiempo.
Pero ¿qué es :sex? ¿Es dt:sex más robusto? ¿Dónde puedo encontrar documentación?
Recopilemos y compartamos algunas ideas. Por favor, compartan sus opiniones y corrijan mis publicaciones si encuentran algún error.
Mis 5 centavos:
Automatización y scriptingRe: referencia de columna robustaEn JSL, una misma referencia de columna :sexo (o dt:sex ) se puede utilizar de dos maneras:
# 1) como referencia a una columna
:sex << get name;
Data Table( "Big Class Families" ) << Distribution( Nominal Distribution( Column( :sex ) ));
... y el número 2
para recuperar la entrada de la fila actual en esta columna, como en:
[editar]: ¡no!
"Se utiliza en fórmulas de columna y, por lo general, puede considerarse como el 'valor de la fila actual'."
Pero hay muchos más casos que también requieren este tipo de :sexo
</CODE></PRE>
<BR />
<P>Tenga en cuenta: en las fórmulas de columna, los siguientes enfoques son equivalentes.</P>
<PRE><CODE class=" language-jsl">new column("s", formula (:sex));
new column("s", formula (:sex[]));
new column("s", formula (:sex[row()]))
row()=5;
s=:sex; // value of the current row
// other cases:
lag(:sex,1); // value of the previous row
Col Mean(:height, :age)); // mean :height of rows with same :age
Para crear un objeto de este tipo a partir de una cadena, existen dos opciones:
column name = "sex";
col= Column (column name); // for the first one (accessing the column)
val = As Column (column name) // for the second one (accessing the column in formulas)
En realidad, hay una tercera opción muy interesante, que aprendí de @jthi :
the universal column reference = Name Expr(As Column(column name))
Se puede usar como :sexo para ambos enfoques: haciendo referencia a la columna y accediendo a la entrada de la fila actual.
Column() vs As Column() vs datable:column vs dt:As name("column")
Re: referencia de columna robusta:sexo parece frágil: ¿qué sucede cuando el usuario cambia el nombre de la columna?
Names Default to Here(1);
dt = Open( "$SAMPLE_DATA/Big Class.jmp" );
x = Name Expr(As column("name"));
Show(Name Expr(x)); // : name
:name << set name("The name");
Show(Name Expr(x)); // :The name
¡Guau, genial! ¡Para nada frágil!
Re: referencia de columna robusta¿Y cuando el usuario cambia la tabla de datos?
Names Default to Here(1);
dt = Open( "$SAMPLE_DATA/Big Class.jmp" );
x = Name Expr(As column("name"));
Show(Name Expr(x));
x[1] = "Marker";
:name << set name("The name");
dt = Open( "$SAMPLE_DATA/Big Class Families.jmp" );
Show(Name Expr(x));
Show(x[1])
El inocente :sexo incluso sabe a qué tabla de datos pertenece. ¡Genial!
Re: referencia de columna robustaAhora, pasemos de 1 columna a 2 columnas:
myList1 = {:name,:sex,:age};
Una forma muy complicada e inútil de crear esta lista es:
myList2 = Eval List({Name Expr(As column(:name)),Name Expr(As column(:sex)),Name Expr(As column(:age))});

Re: referencia de columna robusta¿inútil?
Ya notas la gran diferencia cuando intentas ejecutar el código anterior sin un
dt = Open( "$SAMPLE_DATA/Big Class.jmp" );
La primera línea no tiene en cuenta que no haya una tabla de datos abierta. Al ejecutar la segunda línea, JMP mostrará el siguiente mensaje:

Mejor aún: cuando la lista se crea con el segundo enfoque, las referencias de columna son muy sólidas.
Independientemente de la tabla de datos actual, JMP irá a dt y utilizará las columnas desde allí:
dt = Open( "$SAMPLE_DATA/Big Class.jmp" );
myList1 = {:name,:sex,:age};
myList2 = Eval List({Name Expr(As column(:name)),Name Expr(As column(:sex)),Name Expr(As column(:age))});
dt2= Open( "$SAMPLE_DATA/Big Class Families.jmp" );
dt << Select Rows( [1] ) << Delete Rows; // now dt starts with Louise - there is no Katie anymore!
Show(Eval List(myList1), // Katie? why Katie!!!
Eval List(myList2)); // Louise -> works!

¿Cómo funciona?
Show(Type(myList1[1]), Type(myList2[1]))
Proporciona más información:

La lista simple ( miLista1 ) contiene " Nombres ", *)
La lista complicada ( miLista2 ) contiene " Columnas " **)
*) Cuando se evalúa un nombre , JMP sigue una regla específica para determinar qué significa este nombre:
https://www.jmp.com/support/help/es/19.0/#page/jmp/rules-for-resolving-names.shtml
Entre los roles, JMP buscará una columna en la tabla de datos actual ( dt2 ).
**) Para una columna , JMP solo tiene que ir a LA tabla de datos (" dt ") y acceder a la columna.
¡Muy robusto!
Re: referencia de columna robustaName Expr(As column(:col))
¡Es tan genial!
Re: referencia de columna robustaLa función Column() funciona en muchas situaciones y es bastante flexible con respecto al formato del nombre de la columna.
Distribution(
Continuous Distribution( Column( :Random Normal )),
Continuous Distribution( Column( "Random Normal" )),
Continuous Distribution( Column( :"Random Normal"n )),
Continuous Distribution( Column( "Random Normal"n )),
Process Capability( 0 ) )
Re: referencia de columna robustaInteresante: cuando se solicitan listas de columnas, las funciones JSL devuelven listas de nombres , no listas de columnas.
Names Default to Here(1);
dt = Open( "$SAMPLE_DATA/Big Class.jmp" );
colList = Eval List({Name Expr(As column("sex"))});
write(Name Expr(colList[1]), " is a ", // :sex
Type(Name Expr(colList[1])), "\!n"); // Column -> universal & robust
selectedCols = dt << select columns (:sex) << get selected columns;
write(Name Expr(selectedCols[1])," is a ", // : sex
Type(Name Expr(selectedCols[1])), "\!n"); // Name -> fragile
dt << Group Columns(Item Range( :sex, :height ),"myColGroup");
colsFromColumnGroup = dt << get column group("myColGroup");
Write(Name Expr(colsFromColumnGroup[1]), " is a ", // :sex
Type(Name Expr(colsFromColumnGroup[1])), "\!n"); // Name -> fragile

La diferencia entre Obtener nombres de columnas() y Obtener referencias de columnas() :
ColNames = dt << get column names; // default setting: returns names, not Strings
Write(Name Expr(ColNames[3]), " is a ", // sex (more or less the same as :sex)
Type(Name Expr(ColNames[3])), "\!n"); // Name -> fragile
ColRefs = dt << get column references;
Write(Name Expr(ColRefs[3]), " is a ", // Column("sex"
Type(Name Expr(ColRefs[3])), "\!n"); // Column -> robust, but not :sex, see below

y ahora juguemos con la columna y luego preguntemos por el valor de :sexo en la fila 1:
//hide the column
:sex << set name("hidden");
// who finds it?
row()=1;
Try(Show(Eval(ColList[1])), print(exception_msg));
Try(Show(Eval(colsFromColumnGroup[1])), print(exception_msg));
Try(Show(Eval(selectedCols[1])), print(exception_msg));
Try(Show(Eval(ColNames[3])), print(exception_msg));
Try(Show(Eval(ColRefs[3])), print(exception_msg));

Re: referencia de columna robustaMensaje para llevar a casa:
Con el aprendizaje de
myList2 = Eval List({Name Expr(As column(:name)),Name Expr(As column(:sex)),Name Expr(As column(:age))});
Podemos convertir cualquier lista proporcionada por JMP en una lista robusta de columnas a través de
ColNames = dt << get column names;
colList = Transform Each({col}, ColNames, Name Expr(As Column (col)));
Re: referencia de columna robusta
@Byron_JMP wrote:
La función Column() funciona en muchas situaciones y es bastante flexible con respecto al formato del nombre de la columna.
Distribution(
Continuous Distribution( Column( :Random Normal )),
Continuous Distribution( Column( "Random Normal" )),
Continuous Distribution( Column( :"Random Normal"n )),
Continuous Distribution( Column( "Random Normal"n )),
Process Capability( 0 ) )
Hola @Byron_JMP , uno puede divertirse mucho con Columna() dentro de distribución()
Names Default to Here(1);
dt = Open( "$SAMPLE_DATA/Big Class.jmp" );
Distribution(Continuous Distribution( Column( :height )) );
Distribution(Continuous Distribution( Column( "height")) );
Una referencia a una columna, un nombre... ¡incluso una cadena! Todo funciona.
... hasta que intente utilizar una columna que esté definida fuera del comando Distribución :
col = Column("height");
Show(col); // shows: it's a column
Distribution(Continuous Distribution(col));
Distribution(Continuous Distribution(Eval(col)));
Distribution(Continuous Distribution(Name Expr(col)));
Uno puede probar todos esos trucos esotéricos de manejo de expresiones del tipo "Probémoslos todos, uno de ellos debería funcionar", ¡pero ninguno de ellos funciona!
Siempre la misma pista, pero ¿qué significa?

La solución es muy fácil, pero puede llevar horas si la buscas en el lugar equivocado.
Encuentra la solución por ti mismo antes de abrir 
:mano_con_el_dedo_índice_apuntando_hacia_abajo:
Ver más...
Column( :height ) inside
Distribución continua()
aspecto like
Columna("altura") in
col = Columna("altura");
But it is a
argumento nombrado - like
Fórmula() in
Nueva columna(Fórmula(...)).
So the "obvious" solution is: keep the name of the named argument and place the column inside:
Distribution(Continuous Distribution(Column(col)));
Re: referencia de columna robustaMi enfoque es mucho más simple. Me aseguro de crear mi lista de columnas para el propósito específico que tengo en mente. A veces tengo varias listas de columnas en diferentes formatos.
Names Default To Here( 1 );
dt = Open( "$SAMPLE_DATA/Big Class.jmp" );
text = dt << Get Column Names();
quote = dt << Get Column Names( String );
colformat = dt << get column reference();
quote = dt << Get Column Names( String );
show(text, quote, colformat);
que devuelve:
texto = {nombre, edad, sexo, altura, peso};
cita = {"nombre", "edad", "sexo", "altura", "peso"};
colformat = {Columna("nombre"), Columna("edad"), Columna("sexo"), Columna("altura"), Columna("peso"};
Generalmente uno de los tres funciona, incluso si tengo que recurrir a eval(parse())
Re: referencia de columna robustaBásicamente, estoy de acuerdo. Después de tomar algunas precauciones, los nombres no son muy peligrosos:
Se puede discutir si es inteligente cambiar el nombre de una columna después de crear una lista de columnas y luego preguntarse o quejarse de que el nombre anterior ya no funciona.
Y cuando se trabaja con dos tablas, uno debe asegurarse de que la tabla de datos correcta sea la tabla de datos actual().
Lo mismo con los nombres de las columnas:
Se puede asumir que JMP maneja los nombres de columnas correctamente, incluso con letras mayúsculas y espacios. [encontrar el enlace]
O uno puede ser cauteloso y seguir algunas reglas (sin colisiones de nombres, variables y nombres de columnas; precaución con el espacio, ...) y la mayor parte del día vivir seguro sin problemas.
Re: referencia de columna robustaHola @Byron_JMP , para ser exigente...

obtener nombres de columnas() devuelve una lista de nombres; )
Re: referencia de columna robustaHallazgo importante: ¡Acabo de editar una de las primeras publicaciones!
Espero que mis pensamientos sean comprensibles, al menos para algunos usuarios como @Craige_Hales .
Supongo que estos usuarios también compartirán mi asombro/iluminación/alegría y/o ayudarán confirmando que es así, proporcionando una explicación o haciendo correcciones.
Hasta ahora he pensado en Como columna(col) como una forma de recuperar el valor de la fila actual , especialmente en comparación con Columna(col) para el "acceso a la columna" (ya sabe, como en Column(col) << obtener nombre).
Con la implicación inversa:
Siempre que uso :col para algo que no sea el " valor de la fila actual ", cuando quiero reemplazarlo con una variable, no tengo que usar Como columna() , tengo que usar la otra en su lugar , es decir Columna(col).
[Debo admitir que también me desconcertó el nombre:
Como columna () - para la función que hace lo inverso, no obtiene la columna, sino el valor de la fila actual? ¿Estás bromeando?
Otro pensamiento:
Si Como columna(col) funciona en tales casos, entonces es simplemente porque JMP corrige el error del usuario automáticamente, o debido a un efecto esotérico que todos usan pero nadie explica, como en Name expr(As column(col)).
Entonces, ahora me siento muy cómodo después de descubrir: ....]
Esta interpretación debe ser errónea. Se desencadena por un automatismo en JMP que podría seguir la idea:
Como columna(col) da acceso a la columna .
Si se evalúa ( Eval(Como Columna() ...) )i, se convierte a columna(col)[] (también conocido como column(col)[row()]), que permite acceder al valor de la fila actual. Si no se evalúa, pero se utiliza en otras funciones, permite acceder a la columna.
¿Porque pienso que es así?
Names Default to Here(1);
dt = Open( "$SAMPLE_DATA/Big Class Families.jmp" );
row()=10;
Lag(:height); // 60
Show(lag(Column ("height"),1)); // Column("height") !!!
Show(lag(As Column ("height"),1)); // 60 !!!
Col Mean(:height); // 6255
Col Mean(:height, :age); // 60.285...
Show(Col Mean(Column ("height"))); // 62.55 (why does it work? another automatism because it is used so often?)
Try(Show(Col Mean(Column ("height"), :age)),Print(exception_msg)); // !!!
Show(Col Mean(As Column ("height"), :age)); // 60.285...
[activado por https://community.jmp.com/t5/Discussions/Using-numeric-objects-in-a-column-equation/mp/903939/highlight/true#M106270 ]
Re: referencia de columna robustaEn base a este aprendizaje tengo una pregunta específica:
¿Existe una descripción general completa de
- which functions act in the spirit of
Eval(:col), Where(:col=1) and Type(:col) ?
i.e. taking the column :col and interpretándolo como:col[fila()] ?
Ver más...
rw = Row();
Where( :age == Column( "age" )[rw] );
- , ¿y qué funciones simplemente tratan la columna como una columna , sin "agregar [fila] gratis"?
como Col mediana(:col), Lag(:col,1)
¿Qué grupo tiene más miembros?
Re: referencia de columna robustaNo creo que Col Mean funcione muy bien en un guión.
Sin embargo, "60.285714286" es el valor de la fila 10, si se aplicó la fórmula de columna, Col Mean(:height,:age) en una columna de fórmula en la tabla de datos.
Y "62.55" es el valor de la fila 10 si estuviera en una columna de fórmula con Col Mean(;altura).
Esta sería una excelente manera de ocultar la búsqueda de valores en otra tabla, especialmente si la tabla fuera privada.
Re: referencia de columna robustaLo siento, no estoy seguro de entender el punto.
Names Default to Here(1);
dt = Open( "$SAMPLE_DATA/Big Class.jmp" , Private);
col median(dt:height);
vals= dt:height << get values();
vals=dt[0,"height"];
Median(vals);