Flash verliert Variablen während einer Rekursion,...

Marius Heil

Erfahrenes Mitglied
Hi,

ich hab grad das Problem, dass ich in einem Zweidimensionalen Array alle Alles mit allem vergleichen muss. Da macht sich rekursion ganz toll. Witzigerweise verliert Flash die übergebenen Variablen aber nach ein paar Zeilen:
PHP:
//Wir rufen un sere Rekursive funktion mit dem anfangsparameter auf
rekurs("", 0);

//Rekursive Funktion: string der bereits getesteten Zahlen; Nummer des jetzigen Elements: -1 < e < arr.length
function rekurs(t, e){
	trace("1"+t);
	//Für jedes Element
	for (i=0; i<combo[e].length; i++){
		trace("2"+t);
		//Die Variablen durchnummerieren, sonst überschreiben sie sich
		tCount++;
		//WENN Zahl1 UND Zahl2 noch unbenutzt UND nicht undefiniert
		if (   t.indexOf("("+combo[e][i]+")", 0) == -1 && t.indexOf("("+e+")", 0) == -1  && combo[e][i] != undefined){
			//Die Zahlen als benutzt in neuer Variable abspeichern, tCount +1 um einzigkeit der Variablen zu garantieren
			trace("3"+t);
			baum["_"+tCount] = t+"("+combo[e][i]+")("+e+")";
		//Zahlen schon benutzt, trotzdem weiter
		} else {
			baum["_"+tCount] = t;
		}
		//Kette an die nächste rekurs() abgeben, tCoutn wurde jedoch bereits erhöht, also -1
		rekurs(baum["_"+tCount]+"", e+1);
	}
}
Die Funktion muss man nicht verstehen um das Problem zu verstehen.
Wie man sieht hab ich zum testen 3x trace() eingebaut um die Ausgabe zu sehen. Dann hab ich das ganze im Debugger getestet. Bei trace 1 wird als e noch 1 ausgebeben, in t steht sowas wie (2)(3). einen Schritt weiter jedoch, wenn zb die For Schleife anfängt sind e und t wieder 0 und "".
Das passt mir gar nicht, da dadurch ne Endlosschleife entsteht,...

PS: Nicht so sehr von den Kommentaren beeinflussen lassen, die dürfte man eh nciht verstehen :D
Marius
 
Hi,

auf den ersten Blick kann ich nichts gravierendes an der Funktion entdecken. Sinnvoll wäre es, den Inhalt des Arrays "combo" zu kennen (und ggf. den von "baum", wenn in dem Array vorher schon etwas steht).

Flash gibt bei mehr als 255 Rekursionsstufen auf (im Allgemeinen mit einer Fehlermeldung) - wenn "combo[ e ]" lang ist, hast Du (da die Rekursion in der Schleife aufgerufen wird) ggf. sehr viele parallele Aufrufe - vielleicht läuft auch hier etwas schief.

Andernfalls: Vielleicht beschreibst Du einmal, was Du womit vergleichen willst, und was Du Dir als Ergebnis vorstellst - vielleicht gibt es eine günstigere Variante, das Gewünschte zu erreichen.

Gruß
.
 
Hi,

die Datei lässt sich bei mir (und das ist kein kleines System) nicht einmal ausführen (es gibt entweder die Scriptverlangsamungs-Fehlermeldung, oder Flash hängt sich komplett auf). Ich kann mir daher schon vorstellen, dass Du an die Grenzen des Interpreters gelangst und die Variablen einfach vom Stack "rutschen".

Hast Du schon einmal probiert, statt der Schleife ein Intervall oder eine onEnterFrame-Methode zu verwenden?

Gruß
.
 
Hi,

mein Pc ist auch nicht unbedingt schlecht ausgerüstet^^ Aber daran liegts nicht. Du darfst das Script nicht ohne Decompiler ausführen, dadurch, dass die Variable die Rekursion nicht überlebt entsteht schlicht ne Endlosschleife die jede Schleife ne neue Variable anlegt, das führt schnell zu systemabstürzen. Wenn man es allerdings im Debugger aufmacht; nen Breakpoint in Zeile 30 setzt - dann sieht man schön, was er macht, ein paar mal auf weiter drücken und beim 3. Anfahren der Funktion läuft bereits alles schief, Zeile 36 hat er die Variable noch korrekt, in Zeile 38 bei der For schleife stehen die Variablen wieder auf 0.
Lässt sich das, was ich programmiert hab überhaupt mit ner onEnterFrame lösen?
Er soll ja schließlich sowas wie nen Baum aufbauen, zuerst zb 1 Wert, dann 2 Folgende, aus jedem Folgenden zb wieder 3, gibt eine rießen Baumstruktur und wenn jeder Funktionsaufruf seine Anfangsvariablen behalten würde sollte das eigentlich auch gehen,...

Marius
 
Hi,

ich muss gestehen, dass ich Durch Dein Konzept nicht ganz durchsteige.

Kannst Du in eigenen (einfachen) Worten beschreiben, welche Ausgangswerte vorhanden sein können, und was (mit welchem Ergebnis) verglichen werden soll?

Suspekt ist mir auf den ersten Blick der Aufbau in Form von Strings (z.B. "(2)(3)") - möglicherweise wäre eine Objektstruktur (oder auch ein XML-Baum) günstiger und weniger fehleranfällig.

Gruß
.
 
Hi,

danke erstmal für die Mühe, ich probier mich mal möglichst kurz zu fassen:
Die Aufgabe: Größtmöglichste Anzahl von Preiskombinationen (unbekannte anzahl von Preisen im Format: 1.45 oder zb 23.44) finden die, immer 2 zusammengezählt einen Centbetrag von entweder 11, 33, 55, 77 oder 99 ergeben. Die Preisliste ist vorgegeben und wird derzeit noch in Flash direkt eingegeben und beim starten in ein Array eingelesen.
Daraufhin hab ich folgendes programmiert:
Die erste Schleife findet alle Möglichen 2er-Kombinationen und speichert die in einem Zweidimensionalen Array.
Nun gibts das Problem, dass Preise nicht doppelt verwendet werden dürfen, es soll jedoch die größtmögliche Anzahl an Kombinationen herauskommen.
Ich geh dann im zweiten Teil, die rekurs() Funktion, von der ersten Zahl aus.
Angenommen die hat 5 mögliche Kombinationspartner, dann läuft die For-Schleife 5 mal durch und erzeugt für jeden Kombinationspartner nen neuen Aufruf. Gleichzeitig speicher ich ab, ob ein Partner bereits verwendet wurde, das geschieht in baum. Dadurch, dass viele Variablen anfallen, nämlich für jeden Funktionsaufruf eine, dacht ich mir ich speicher die der Übersicht halber in Baum.
Jede erzeugte Kette wird danach wieder an die Funktion geliefert, so wie ich es haben will mit: Den bisherigen Kombinierten Preisen in dieser Kette; Dem Index des nächsten Preises den ich brauche um die möglichen Partner auszulesen.
Und hier ist der Knackpunkt: Es werden zwar mehrer Instanzen aufgerufen, allerdings scheint da was beim Übergeben dieser Variablen schiefzulaufen. Heruauskommen sollte zb "(3)(2)(1)(7)(9)(11)", das hieße dann konkret, er hat Preis 3 mit 2, 1 mit 7 und 9 mit 11 kombiniert, das hieße er darf im weiteren Verlauf keinen dieser Preise mehr verwenden, das lässt sich mit indexOf ja schön auslesen, die Klammern sind einfach nur zum abtrennen der Zahlen und weil ich die Ausgabe so schöner fand als mit zB Punkten dazwischen.

Marius
 
... kann es sein, dass "tCount" die maximale Länge eines assoziativen Arrays übersteigt? (mal ein Schuss ins Blaue).

Ansonsten: Ich probier morgen mal, einen alternativen Vorschlag zu posten.

Gruß
.
 
Hi, kann auch nicht sein :)
Ich habs schließlich im Debugger getestet, der bereits nach 3 Schlefiendurchläufen die Variablen verliert, zu der Zeit wurden höchstens 3 Variablen gesetzt und die Strings beinhalten 2 Zahlen,...
 
hmm ... dennoch würde ich statt einem assoziativen Array:
Code:
baum["_"+tCount] = sonstwas
mal ein "normales" probieren, und mit push arbeiten (Du sparst Dir dann zumindest "tCount":
Code:
baum.push(sonstwas);

Wie gesagt: Morgen oder spätestens übermorgen (bis wann muss es denn fertig sein?) nehme ich mich dem Problem mal an. Am Code ansich kann ich tatsächlich keinen Fehler entdecken.

Gruß
.
 
Hi,
dank dir vielmals, Einsendeschluss ist erst am 14. nächsten Monats, sidn also noch ein paar Tage, 4 vorher werd ichs einschicken, bis dahin muss ich noch 2 Aufgaben machen, die scheinen aber weit einfacher zu sein. Eine Simulation für Gravitation hab ich bereits programmiert, und ne andere auch.
Wenn man im Code nix außergewöhnliches findet ist das umso ärgerlicher.
Danke für den tipp mit push, das könnte mir wirklich ein wenig Arbeit ersparen, kannte ich noch gar nicht.

Marius
 
Zurück