Ich versuche, verschachtelte Schleifen zu erstellen:
Erstellen Sie in der ersten Schleife einige Spalten und fügen Sie eine Formel hinzu
In der zweiten Schleife werden einige weitere Spalten erstellt, und die Formel benötigt Spalten aus der ersten Schleife
Meine Frage befindet sich in der zweiten Schleife. Ich kann die Spaltennamen in der Formel nicht korrekt einrichten, indem ich eval() + substitue() + expr() verwende.
Names Default To Here( 1 );
dt = current data table();
a=3;
b=3;
alist = {1,2,3};
blist = {1,2,3};
// In actual script, above numbers will come from H list box input
For (i=1, i <= a, i++,
dt << New Column( eval("a_" || char(alist[i])), Formula(:gap*2) );
col = "a_" || char(alist[i]);
For (k=1, k <= b, k++,
eval(
substitute(
Expr(
dt << New Column( eval("a_" || char(alist[i]) || " b_" || char(blist[k])), Formula( If(:vvv > 0 & (:vvv < blist[k] ),1,0) ) );
),
Expr(vvv),
col //here gives wrong result, the formula doesn't really use column a_1, a_2, a_3, instead it use "a_1"......etc
)
)
)
)
Das könnte eine Idee geben
Names Default To Here(1);
dt = Open("$SAMPLE_DATA/Big Class.jmp");
a = 3;
b = 3;
alist = {1, 2, 3};
blist = {1, 2, 3};
// In actual script, above numbers will come from H list box input
For(i = 1, i <= a, i++,
new_col = dt << New Column(Eval("a_" || Char(alist[i])), Formula(:height* 2));
For(k = 1, k <= b, k++,
Eval(Substitute(
Expr(dt << New Column("a_" || char(new_col << get name) || " b_" || char(blist[k]),
Formula(If(vvv > 0 & (vvv < www), 1, 0))
)),
Expr(vvv), Name Expr(AsColumn(new_col)),
Expr(www), blist[k]
)
)
);
);
Bearbeiten:
Wenn Sie JMP16+ haben, könnten Sie die Schleifen in „For Each“ ändern (dies verwendet auch Eval(EvalExpr()) anstelle von Eval(Substitute()), da es meiner Meinung nach in einfachen Fällen wie diesem klarer ist
Names Default To Here(1);
dt = Open("$SAMPLE_DATA/Big Class.jmp");
alist = {1, 2, 3};
blist = {1, 2, 3};
For Each({aval}, alist,
new_col = dt << New Column("a_" || Char(aval), Formula(:height * 2));
For Each({bval}, blist,
col_title = "a_" || Char(new_col << get name) || " b_" || Char(bval);
Eval(EvalExpr(
dt << New Column(col_title, Numeric, Nominal, Formula(
If(0 < Expr(Name Expr(As Column(dt, new_col))) < Expr(bval),
1
,
0
)
))
));
);
);
Damit ist meine Frage gelöst, danke. Und die zweite Methode sieht noch klarer aus
Noch eine Frage: Ich verwende blist[k] direkt in meinem Code, und Sie verwenden „www“ und ersetzen es dann. Beide liefern das gleiche berechnete Ergebnis
Liegt es daran, dass meine Methode eine Variable blist[k] in der Formel hinterlässt, die schief gehen kann, wenn der Benutzer versucht, die Formel erneut anzuwenden, nachdem der Code ausgeführt wurde?
Kurze Antwort:
Ja. Wenn Sie den Bezug zu blist oder k verlieren, kann die Formel nicht neu ausgewertet werden. Und wenn Formeln neu ausgewertet werden, während Sie noch Zugriff auf beide haben, Dasselbe k wird für alle Formeln verwendet, die falsche Antworten liefern würden. Sie sollten dies durch Ausführen testen können dt << Formeln erneut ausführen;
Mehr sehen...
Lange Antwort:
Ja, wenn Sie sie nicht auswerten, bleibt blist[k] in Ihrer Datentabelle. Dies wäre dann der letzte k-Wert, den Sie in allen Formeln haben (Problem, wenn Formeln neu ausgewertet werden, während Sie noch Zugriff auf blist und k haben) und wenn die Tabelle erneut geöffnet wird (oder Sie aus irgendeinem Grund den Zugriff auf blist/k verlieren). die wird es überhaupt nicht geben. Solche Fälle können in der Regel leicht anhand der Formel überprüft werden


Ein anderer Ort, an dem dies leicht passieren kann, sind grafische Skripte, und Sie können sie ebenfalls im Grafikskriptfenster sehen</CODE></P>
<P> </P>
<PRE><CODE class=" language-jsl">Names Default To Here(1);
dt = open("$SAMPLE_DATA/Big Class.jmp");
gb = dt << Graph Builder(
Variables(X(:weight), Y(:height), Overlay(:sex)),
Elements(Points(X, Y, Legend(9)), Line Of Fit(X, Y, Legend(11)))
);
line = 60;
framebox = Report(gb)[frame box(1)];
framebox << Add Graphics Script(
H Line(line)
);
line = 70;
framebox << Add Graphics Script(
H Line(line)
);
Sie erhalten zwei solcher Skripte

und es wird keine Linie auf Y = 60 geben. Auch wenn Sie das Graph Builder-Skript kopieren, wird dort eine Zeile anstelle von Werten angezeigt
Graph Builder(
Variables(X(:weight), Y(:height), Overlay(:sex)),
Elements(Points(X, Y, Legend(9)), Line Of Fit(X, Y, Legend(11))),
SendToReport(
Dispatch(
{},
"Graph Builder",
FrameBox,
{Add Graphics Script(9, Description(""), H Line(line)),
Add Graphics Script(10, Description(""), H Line(line))}
)
)
)
Eine einfache Lösung hierfür ist die Auswertung der Werte
Names Default To Here(1);
dt = open("$SAMPLE_DATA/Big Class.jmp");
gb = dt << Graph Builder(
Variables(X(:weight), Y(:height), Overlay(:sex)),
Elements(Points(X, Y, Legend(9)), Line Of Fit(X, Y, Legend(11)))
);
line = 60;
framebox = Report(gb)[frame box(1)];
Eval(EvalExpr(
framebox << Add Graphics Script(
H Line(Expr(line))
);
));
line = 70;
Eval(EvalExpr(
framebox << Add Graphics Script(
H Line(Expr(line))
);
));
Generell würde ich sagen, dass es manchmal eine gute Idee sein kann, alle Variablennamen auszuwerten, wenn Sie damit beginnen, Variablennamen durch die Auswertung in Werte zu ersetzen. Damit meine ich in diesem Fall, dass es von Vorteil sein könnte, auch den Spaltentitel zu bewerten
Eval(EvalExpr(
dt << New Column(Expr(col_title), Numeric, Nominal, Formula(
If(0 < Expr(Name Expr(As Column(dt, new_col))) < Expr(bval),
1
,
0
)
))
));
);
Dies hat beispielsweise zusätzliche Vorteile, wenn Sie Ihren Code debuggen. Unten finden Sie ein einfaches Beispiel für die Erstellung einer Spalte aus einer Referenz und mit einer Variablen, die einwandfrei funktioniert
Names Default To Here(1);
dt = Open("$SAMPLE_DATA/Big Class.jmp");
new_col = dt << New Column("Test", Numeric, Continuous, << Set Each Value(1));
col_title = (new_col << get name) || "* var";
var = 2;
Eval(EvalExpr(
dt << New Column(col_title, Numeric, Nominal, Formula(
Expr(NameExpr(AsColumn(dt, new_col))) * Expr(var)
));
));
aber wenn Sie Probleme hätten, könnten Sie einfach EvalExpr() und alles darin markieren und diesen Teil des Skripts ausführen

col_title wird nicht ausgewertet (in diesem Fall kein Problem, ABER es könnte sein, wenn Sie ein komplizierteres Skript hätten) und indem Sie (in diesem Fall) einfach einen weiteren Expr() hinzufügen, erhalten Sie mehr Informationen darüber, was wirklich vor sich geht
