flash actionscript-3 event-handling garbage-collection weak-references

flash - Aclaraciones sobre las referencias débiles en los oyentes ActionScript



actionscript-3 event-handling (1)

Entiendo cómo funcionan las referencias débiles, pero estoy un poco confundido con respecto a su uso en los oyentes del evento actionscript. Considera el siguiente ejemplo:

public class Rectangle extends MovieClip { public function Rectangle() { var screen:Shape=new Shape(); screen.addEventListener(MouseEvent.MOUSE_OUT, new Foo().listen, false, 0, true); addChild(screen); } } public class Foo extends MovieClip { public function listen(e:MouseEvent):void { trace("tracing"); } }

Ahora aquí, dado que solo hay una referencia débil a Foo, ¿no se recolectaría el recolector de basura del evento si el colector de basura se ejecuta y el código deja de funcionar como se esperaba?

¿El escenario de escucha de eventos débiles se prescribe solo para métodos de escucha de eventos dentro de la misma clase que a continuación?

public class Rectangle extends MovieClip { public function Rectangle() { var screen:Shape=new Shape(); screen..addEventListener(MouseEvent.MOUSE_OUT, listen, false, 0, true); addChild(screen); } public function listen(e:MouseEvent):void { trace("tracing"); } }

En el escenario anterior, ¿es así de débil el hecho de que los oyentes ayuden?

Si el objeto Rectangle no tiene otras referencias, entonces es un candidato para la recolección de basura, pero dado que hay un detector de eventos dentro del objeto, el despachador de eventos contiene una referencia al objeto, aunque no haya otras referencias al objeto ( que no sea el celebrado por el oyente del evento). Por lo tanto, se evita que sea basura recolectada. ¿Es esta la razón por la que se prescriben los oyentes de eventos débiles? ¿Es el reproductor flash tan ingenuo que no puede entender que el detector de eventos esté definido dentro del mismo objeto?


La regla básica para la recolección de basura en Flash es que si se hace referencia (directa o indirectamente) a un objeto desde la línea de tiempo, no se puede recolectar basura. Esto significa que si una instancia de su clase no se referencia desde ningún lugar en la lista de visualización raíz (o por un objeto que a su vez se hace referencia desde la raíz, et c recursivamente), se recopilará independientemente de si tiene referencias a sí mismo.

Esto también significa que dos objetos que se referencian entre sí, pero que no están siendo referenciados de ninguna manera desde la lista de visualización de la raíz, deberían ser elegibles para la recolección de basura.

La opción de referencia débil en los detectores de eventos es principalmente para que no tenga que eliminar el detector de eventos manualmente. Personalmente, tiendo a no usarlo, porque me gusta tener el control total de cuándo se marcan los objetos para la recolección de basura.

Entonces, en su primer ejemplo, la instancia de Foo es elegible en todos los casos para la recolección de basura. En el segundo, si la instancia Rectangle se puede recolectar basura o no depende de si se hace referencia a ella desde la lista de visualización. La bandera useWeakReference en este sentido no hace diferencia.

De la documentación aquí :

Las funciones de miembro de nivel de clase no están sujetas a la recolección de elementos no utilizados, por lo que puede establecer useWeakReference en true para las funciones de miembro de nivel de clase sin someterlas a la recolección de elementos no utilizados. Si establece useWeakReference en true para un oyente que es una función interna anidada, la función será recogida de basura y ya no será persistente. Si crea referencias a la función interna (guárdela en otra variable), entonces no se recolecta basura y permanece persistente.