<meta http-equiv="Content-Type" content="text/html; charset=UTF-8" />Uso 2 metodi per creare colonne formula a seconda che io sappia di quante variabili ha bisogno la formula
- Espr e sostituto sono facili da leggere. La sezione 1 nel codice crea diverse colonne formula per ogni variabile in un elenco per mean( var, byvar )
- Parse e eval e possibilmente eval insert creano una singola colonna formula che richiede un numero di variabili, il numero e il nome impostati dall'elenco delle variabili.
- Le sezioni 2a e 2b funzionano e sono funzionalmente equivalenti
- Le sezioni 2c e 2d non corrono, ma sembrano un percorso verso una soluzione elegante
Vorrei idee per creare pratiche migliori e apprezzerei consigli
Nomi Predefinito A Qui( 1 );
n=tabella();
dtnms={};
Se(
n==0, tcc=1,
n==1, If(current data table() << get name == "Big Class", dtc=0, dtc=1) , // else
for(ii=1, ii <= n, ii++, insert into(dtnms, data table(ii) << getname));
if(contiene(dtnms, "Big Class") > 0, dtc=1, dtc=0);
);
if (dtc,dt = Open( "$SAMPLE_DATA/Big Class.jmp" ), dt = data table("Big Class"));
// Sezione 1: aggiungi diverse colonne di formule inserendo le variabili in modo dinamico.
Modulo1=espr(
form1col=dt << nuova colonna(Nome, formula(col mean(As Column(YVar), As Column(ByVar))))
);
VarList={"sesso", "altezza", "peso"};
For(ii=2, ii <= N elementi(VarList), ii++,
Eval(Sostituisci(Nome expr(form1),
expr(Nome), ListaVar[ii]||" Medie",
expr(YVar), ListaVar[ii],
expr(PerVar), ListaVar[1],
));
);
// Sezione 2: Calcola la media delle colonne nell'elenco delle variabili
// Metodo 2a Il metodo funziona ma è difficile eseguire il debug
VarList={"altezza", "peso", "età"};
Formtxt1 = "formcol = dt << nuova colonna(\!"Metodo a: Media\!", formula(media( ";
Formtxt2 = "As Column(\!""||VarList[1]||"\!")";
Se(
N Items(VarList)==2, Formtxt2 ||= ", As Column(\!""||VarList[2]||"\!")",
N elementi(VarList)>2, For(ii=2, ii <= N elementi(VarList), ii++,
Formtxt2 ||= ", As Column(\!""||VarList[ii]||"\!")"
)
);
Formtxt=Formtxt1||Formtxt2||");";
eval(analizza(Formtxt));
// Metodo 2b: Un po' più facile da vedere
col4=espr(
NewCol1=dt << New Column("Metodo b: Media di "||_nomi_);
);
form4txt="NewCol1 <
VarList={"altezza", "peso", "età"};
VarRef = eval list(dt << get Colonna Riferimento(VarList));
_Vars_ = "As Column( \!"" || ConCat Items(VarList, "\!"), As Column( \!"") || "\!")";
form4txta = Eval Insert(form4txt);
Eval(Sostituisci(Nome expr(col4),
expr(_names_), concat Items(VarList,", ",)
));
Eval(Analizza(form4txta)); //Parse rende il testo un expr che viene valutato
// *************************************** //
// ************* Non funziona ************* //
//Metodo 2c: penso che questo sarebbe il migliore, ma non riesco a correggerlo - Ho ancora un elenco
modulo3=espr(
NewCol=dt << Nuova Colonna("Media di "||_nomi_, formula(Media(_Vars_ )));
);
VarList={"altezza", "peso", "età"};
VarRef = eval list(dt << get Colonna Riferimento(VarList));
Eval(Sostituisci(Nome expr(form3),
expr(_names_), concat Items(VarList,", ",),
expr(_Vars_), VarRef
));
// Metodo 2d: utilizzo di un ciclo, ma ancora errato
modulo4=espr(
NewCol=dt << Nuova Colonna("Media di "||_nomi_, formula(Media(_Vars_ )));
);
VarList={"altezza", "peso", "età"};
VarRef = eval list(dt << get Colonna Riferimento(VarList));
Form4a =Sostituisci(Nome expr(form4),
expr(_names_), concat Items(VarList,", ",)
);
For(ii=1, ii <= N elementi(VarList), ii++,
form4a=Sostituisci(Nome expr(form4a),
expr(_Vars_), expr(VarRef[ii], _Vars_)
);
);
Eval(Substitute(Nome expr(form4a),
espr(_Vars_), ""
));
// *************************************** //
// ************* Non funziona ************* //
Bella raccolta di metodi diversi.
Ultimamente preferisco lavorare con le espressioni piuttosto che con le stringhe in casi come questo. Per impostare una formula tramite JSL, per prima cosa costruisco l'espressione usando EvalExpr(), che poi inserisco con NameExpr() per evitare la valutazione in fase di esecuzione.
Di seguito sono riportati due esempi basati su un elenco di nomi di colonne o su un elenco di stringhe, quest'ultimo è un po' più impegnativo.
dt = Aprire ( "$SAMPLE_DATA/Classe grande.jmp" ) ;
// 1. Elenco dei nomi delle colonne
L1 = { età , altezza , peso } ; // cioè dt<
modulo1 = Espr ( Significare ( Espr ( L1 ))) ;
form1col = dt << Nuova Colonna ( Oggetti concatenati ( Parole ( Car ( L1 ) , "{}," )) || " Media" , formula ( Nome Espr ( modulo1 ))) ;
// 2. Elenco delle stringhe
L2 = { "età" , "altezza" , "peso" } ; // cioè dt<
modulo2 = Espr (
Significare (
Espr (
Ripetere (
io = 0 ;
{ io ++ ; Espr ( Come Colonna ( Espr ( L2 [ io ])))} ;,
N articoli ( L2 )
)
)
)
) ;
form2col = dt << Nuova Colonna ( Oggetti concatenati ( L2 ) || " Media" , formula ( Nome Espr ( modulo2 ))) ;