Ich habe diesbezüglich bereits den JMP-Support kontaktiert und dies wurde als Fehler markiert. Hier ist ein einfacher „realer“ Fall, in dem dieser Fehler beobachtet werden konnte
Names Default To Here(1);
dt = Open("$SAMPLE_DATA/Big Class.jmp");
f2 = function({}, {Default Local},
Summarize(dt, uniq_values = by(:sex));
all_sex_values = dt[0, "sex"];
//dt = dt; // don't remove, it just works
For Each({uniq_value}, uniq_values,
cur_sex_rows = Loc(all_sex_values, uniq_value);
show(all_sex_values, uniq_value, cur_sex_rows, dt); // dt goes poof inside for each
vals = Transform Each({val}, dt[cur_sex_rows, "age"], Output("List"), Char(val));
show(vals);
);
);
f2();
all_sex_values = {"F", "F", "F", "F", "F", "M", "M", "M", "F", "F", "F", "M", "M", "M", "M", "F", "F", "F", "F", "F", "M", "M", "M", "M", "M", "M", "M", "F", "F", "M", "M", "M", "M", "M", "F", "F", "M", "F", "M", "M"};
uniq_value = "F";
cur_sex_rows = [1, 2, 3, 4, 5, 9, 10, 11, 16, 17, 18, 19, 20, 28, 29, 35, 36, 38];
dt = ␀;
argument value is invalid in access or evaluation of 'Transform Each' , Bad Argument(dt[cur_sex_rows, "age"]), Transform Each/*###*/({val}, dt[cur_sex_rows, "age"], Output("List"), Char(val))
at line 15 in mypath
Ich habe an einem Skript gearbeitet, in dem ich einen kleinen Teil davon verschlüsseln muss, also habe ich den größten Teil des Codes, den ich verschlüsseln muss, in eine einzelne Funktion verpackt, um das Risiko zu minimieren, dass meine Variablen verloren gehen (in diesem Fall bin ich so faul). ). Beim Schreiben dieser übermäßig großen Einzelfunktion fiel mir auf, dass in meiner For Each-Schleife die Fehlermeldung „Argumentwert ist ungültig“ angezeigt wurde, obwohl alle Variablen definiert waren. Ich habe einige Tests durchgeführt und herausgefunden, dass for Each (und andere Each-Schleifen) Default Local nicht korrekt verarbeiten (oder es schien so). Nachfolgend finden Sie zwei Beispiele
Names Default To Here(1);
thing = Expr(
Summarize(dt, uniq_values = by(:sex));
all_sex_values = dt[0, "sex"];
For Each({uniq_value}, uniq_values,
cur_sex_rows = Loc(all_sex_values, uniq_value);
vals = Transform Each({val}, dt[cur_sex_rows, "age"], Output("List"), Char(val));
show(vals);
);
);
f1 = function({}, {Default Local},
thing;
);
f2 = function({}, {Default Local},
Summarize(dt, uniq_values = by(:sex));
all_sex_values = dt[0, "sex"];
//dt = dt; // don't remove, it just works
For Each({uniq_value}, uniq_values,
cur_sex_rows = Loc(all_sex_values, uniq_value);
show(all_sex_values, uniq_value, cur_sex_rows, dt); // dt goes poof inside for each
vals = Transform Each({val}, dt[cur_sex_rows, "age"], Output("List"), Char(val));
show(vals);
);
);
f3 = function({}, {all_sex_values, cur_sex_rows},
Summarize(dt, uniq_values = by(:sex));
all_sex_values = dt[0, "sex"];
For Each({uniq_value}, uniq_values,
cur_sex_rows = Loc(all_sex_values, uniq_value);
vals = Transform Each({val}, dt[cur_sex_rows, "age"], Output("List"), Char(val));
show(vals);
);
);
dt = Open("$SAMPLE_DATA/Big Class.jmp");
Print("Thing Expr");
Try(thing, show(exception_msg));
Print("\!NThing Expr inside Function");
Try(f1(), show(exception_msg));
Print("\!NThing Function Only default local");
Try(f2(), show(exception_msg));
Print("\!NThing Function Only local list");
Try(f3(), show(exception_msg));
Close(dt, no save);
Names Default To Here(1);
my_val = 1;
my_func1 = function({}, {Default Local},
show(my_val);
);
my_func2 = function({}, {Default Local},
my_func1();
);
my_func22 = function({}, {Default Local},
my_func2();
);
my_func222 = function({}, {Default Local},
my_func = function({}, {Default Local},
show(my_val);
);
my_func();
);
my_func3 = function({}, {Default Local},
my_func1(); // even this goes null
For Each({z}, {"b","c"}, show(my_val));
);
my_func1();
my_func2();
my_func22();
my_func222();
my_func3();
Ich bin (heimlich) stolz darauf, dass ich dies (vorerst) meinem Produktionsskript überlassen kann, da ich diese noch nicht hatte (aber ich war hilfreich und habe dort zumindest die Fallnummer für mein zukünftiges Ich hinzugefügt).
dt = dt; // don't remove, it just works (JMP Support Case 00075244)
Ich habe diesbezüglich eine Antwort von JMP-Supportmitarbeitern erhalten, die den JMP-Entwickler kontaktiert hatten:
Dies scheint eine schlechte Interaktion zwischen Function Default Local und den Each-Funktionen zu sein. Hier ist ein fehlgeschlagener Test:
ut test("EachLoop", "Default Local in Body Expr", Expr(
defloc = 5;
f = Function({}, {Default Local}, Transform Each({x}, 1::5, x*defloc));
ut assert that(Expr(f), [5 10 15 20 25])
));
Da es sich bei defloc um einen nicht qualifizierten Namen handelt, der im Funktionskörper erscheint, wird er als Standardlokal markiert. Das bedeutet, dass JMP automatisch ein Local erstellt, wenn wir auf das Symbol schreiben. Wenn es jedoch wie im obigen Skript daraus liest, sollte es den lokalen Frame überspringen und zum nächsten Frame und zum nächsten weitergehen, bis Here und Global. Dies ist das erwartete Verhalten und das, das Sie erhalten, wenn Sie defloc außerhalb der Each-Funktion lesen. Wenn Sie jedoch in die Each-Funktion hineinlesen, bricht dieser Prozess aus irgendeinem Grund ab. Möglicherweise, weil die Each-Funktion selbst einen anderen Frame einführt, da sie auch lokale Frames haben kann.
Das dt = dt ist eine Problemumgehung, ebenso wie das vollständige Vermeiden von Default Local.