Cómo pasar columnas como argumentos para una funciónEstoy intentando crear una función que cree una nueva columna y establezca una fórmula:
my_function = Function( {name, col1, col2},
dt << New Column( name, Character);
Column(dt,name) << Set Formula(
If(
:col1 == "Positive" & :col2 ==
"TRUE",
"True Positive",
If(
:col1 == "Negative" & :col2== "TRUE",
"False Positive",
If(
:col1 == "Negative" & :col2 == "FALSE",
"True Negative",
If(
:col1 == "Positive" & :col2 == "FALSE",
"False Negative",
"?"
)
)
)
)
);
);
Pero cuando miro la fórmula creada, pasa a col1 en lugar de a la cadena detrás de ella.
Llamando a la función como:
my_function("Nueva columna", Columna("columna_1"), Columna("columna_2"));
Automatización y secuencias de comandosRe: Cómo pasar columnas como argumentos de una funciónAquí hay una manera de manejar esto.

Names Default To Here( 1 );
dt = New Table( "Example",
Add Rows( 5 ),
New Column( "a",
Character,
"Nominal",
Set Values( {"Positive", "Positive", "Negative", "Negative", "unknown"} )
),
New Column( "b",
Character,
"Nominal",
Set Values( {"TRUE", "FALSE", "TRUE", "FALSE", ""} )
)
);
my_function = Function( {name, col1, col2},
dt << New Column( name, Character );
Eval(
Eval Expr(
Column( dt, name ) << Set Formula(
If(
as Column( Expr( col1 ) ) == "Positive" & as Column( Expr( col2 ) )
== "TRUE", "True Positive",
as Column( Expr( col1 ) ) == "Negative" & as Column( Expr( col2 ) )
== "TRUE", "False Positive",
as Column( Expr( col1 ) ) == "Negative" & as Column( Expr( col2 ) )
== "FALSE", "True Negative",
as Column( Expr( col1 ) ) == "Positive" & as Column( Expr( col2 ) )
== "FALSE", "False Negative",
"?"
)
)
)
);
);
my_function( "new column", "a", "b" );Re: Cómo pasar columnas como argumentos de una funciónSi prefiere utilizar columnas (también conocidas como: edad) en lugar de cadenas ("edad") para hacer referencia a las columnas, hay dos problemas que resolver:
- una función generada manualmente evalúa sus argumentos.
Entonces, si usa una columna como argumento de función, Jmp la evaluará (es decir, devolverá el valor de la fila actual *)
→ para prevenirlo:
envolver la columna con Name Expr()
- En la mayoría de los casos, Jmp no reemplaza las variables (como "col1") con su valor (la columna respectiva),
por ejemplo, en nueva columna() o << establecer fórmula
→ para obligar a Jmp a hacerlo:
utilice Eval(Eval Expr( .... Expr( xyz ) ... ) para evaluar xyz antes de evaluar la parte restante.
2b) para evitar que Jmp sobreevalúe la referencia de la columna (como en *), use Name Expr() nuevamente ,
entonces, en combinación , use
Expr(Nombre Expr(colX))
... donde quieras usar la columna
en total:
Names Default To Here(1);
dt = Open("$SAMPLE_DATA/Big Class.jmp");
my_function = Function({name, col1, col2},
new_col = Eval(Eval Expr(New Column(name, Character, Formula(Expr(Name Expr(col1)) /* #2b */ - Expr(Name Expr(col2))/* #2b */ )))); // #2
);
col = my_function("diff", Name Expr(:height), Name Expr(:weight)); //#1
Re: Cómo pasar columnas como argumentos de una funciónMuchas gracias, exactamente lo que necesitaba. ¡Además el elseif es mucho mejor! Gracias por compartir
Re: Cómo pasar columnas como argumentos de una funciónSiempre paso columnas con nombres (y referencias de tablas). Y si necesita una fórmula, use Insertar una expresión en otra usando los métodos Eval Insert, Eval Expr, Parse y Substitute para construirla (prefiero Eval(EvalExpr()) pero en su caso usaría Eval(Substitute()). Aquí es una opción cómo podrías manejar esto
Names Default To Here(1);
dt = Open("$SAMPLE_DATA/Big Class.jmp");
my_function = Function({dt, name, col1, col2},
new_col = Eval(Substitute(
Expr(dt << New Column(name, Character, Formula(
If(_col1_ == "Positive" & _col2_ == "TRUE",
"True Positive",
If(_col1_ == "Negative" & _col2_== "TRUE",
"False Positive",
If(_col1_ == "Negative" & _col2_ == "FALSE",
"True Negative",
If(_col1_== "Positive" & _col2_ == "FALSE",
"False Negative",
"?"
)
)
)
)
))),
Expr(_col1_), Name Expr(AsColumn(dt, col1)),
Expr(_col2_), Name Expr(AsColumn(dt, col2))
));
return(new_col)
);
col = my_function(dt, "test", "name", "sex");
Además, JMP tiene la opción de usar elseif (aunque no esté escrito) y podría funcionar en su caso si se anidan varias declaraciones if.
Ver más...
Names Default To Here(1);
dt = Open("$SAMPLE_DATA/Big Class.jmp");
my_function = Function({dt, name, col1, col2},
new_col = Eval(Substitute(
Expr(dt << New Column(name, Character, Formula(
If(_col1_ == "Positive" & _col2_ == "TRUE",
"True Positive",
_col1_ == "Negative" & _col2_== "TRUE",
"False Positive",
_col1_ == "Negative" & _col2_ == "FALSE",
"True Negative",
_col1_== "Positive" & _col2_ == "FALSE",
"False Negative"
,
"?"
),
))),
Expr(_col1_), Name Expr(AsColumn(dt, col1)),
Expr(_col2_), Name Expr(AsColumn(dt, col2))
));
return(new_col)
);
col = my_function(dt, "test", "name", "sex");