2009-09-10 6 views
0

Il me manque clairement quelque chose ici.AS3 Dynamic Class Noms des méthodes dynamiques

J'ai besoin de remplir des méthodes de classe dynamique AS3 à partir d'un tableau (voir l'exemple stupide ci-dessous). Mais quand j'appelle ces méthodes, toutes semblent être la même méthode. Dans l'exemple ci-dessous, toutes les méthodes sont foobar1.

Si je crée des méthodes à la main, sans boucle, tout va bien.

Des indices?

package foo 
    { 
    public class Bar 
    { 
     public function testDynamicClassSanity():void 
     { 
     var foo:Foo = new Foo(); 
     var methods:Object = { foobar1: 101, foobar2: 201, foobar3: 301 }; 

     for (var key:String in methods) 
     { 
      var val:Number = methods[key]; 
      foo[key] = function():Number 
      { 
      return val; 
      }; 
     } 

     // Next trace prints 
     // 101 = 101 201 = 101 301 = 101 
     trace(
      101, "=", foo.foobar1(), 
      201, "=", foo.foobar2(), 
      301, "=", foo.foobar3() 
     ); 
     } 
    } 
    } 

    internal dynamic class Foo 
    { 
    }; 

Répondre

4

Je suppose que le problème est dans la portée de val - vous assumez la portée est la boucle, mais ce n'est pas le cas dans AS3, la portée est la fonction. Ai-je raison de dire que tous vos appels retournent 301? Mise à jour: Travailler autour du problème que vous rencontrez (la variable val étant référencée et seulement résolue plus tard au lieu d'être «copiée» dans votre fonction) est assez lourde: Selon votre cas d'utilisation, vous pouvez inspecter les appels de méthode et recherchez simplement le résultat souhaité dans la table en utilisant la fonctionnalité fournie par Proxy.

+0

Oui, vous avez raison (presque, c'est 101). J'ai mis à jour la question. Comment travailler autour de ça alors? –

+1

Ah, je supposais que la boucle for itérerait sur les propriétés de l'objet dans l'ordre où elles ont été définies, c'était bien sûr stupide de supposer :-) Cochez cette autre question http://stackoverflow.com/questions/422784/ how-to-fix-closure-problem-in-actionscript-3-as3 pour un conseil. –

2

Je pense que votre problème est la portée de la variable var. Essayez cette modification:

for (var key:String in methods) 
{ 
    var val:Number = methods[key]; 
    foo[key] = function (valInternal:Number) { 
    return function():Number 
    { 
     return valInternal; 
    }; 
    }(val); 
} 

(l'astuce ci-dessus fonctionne en Javascript pour contourner un problème similaire ... Je parie qu'il est applicable à AS3)

+0

Je crois que ça devrait être "return valInternal", non? –

+0

oui, fixé ..... – jsight

1

Pour les disques, je posterai ici la version corrigée de la testDynamicClassSanity() fonction:

public function testDynamicClassSanity():void 
    { 
     var foo:Foo = new Foo(); 
     var methods:Object = { foobar1: 101, foobar2: 201, foobar3: 301 }; 

     // We have to introduce new scope 
     var makeCallback:Function = function(result:Number):Function 
     { 
     return function():Number 
     { 
      return result; 
     } 
     } 

     for (var key:String in methods) 
     { 
     foo[key] = makeCallback(methods[key]) 
     } 

     // Prints as intended 
     // 101 = 101 201 = 201 301 = 301 
     trace(
      101, "=", foo.foobar1(), 
      201, "=", foo.foobar2(), 
      301, "=", foo.foobar3() 
     ); 
    } 
Questions connexes