![]() |
|
||||||||||
|
|
|
|||||
|
Товарищи увы, открыл для себя интересную вещь, о которой даже не знал, а может быть, проблема в другом , вообщем :
Есть класс загрузки скинов , и класс в котором идет работа с элементами скина. Рассмоьтрим второй класс Так вот, теперь рассмотрим ситуацию, что инстанс ManagerSkin еще не готов , а так же Skins не прошел инициализацию, напишем : ManagerSkin.setVar(0) // некий метод не имеющий отношение к Skins В итоге после этого, как только инстанс будет создан и будет обращение к element мы получим ошибку. (1009) Тоесть вывод : как только мы первый раз обращаемся к классу со статическими переменными - ВСЯ его статика сразу же инициализируется. Честно говоря, я думал, что инициализация статики происходит ТОЛЬКО после обращения к ней напрямую, и не зависит от того, что ты стучишься к другим переменным.
__________________
Марк Tween |
|
|||||
|
Инициализация статик классов непредсказуема.
Но можно гарантировать выполнение кода перед обращением ленивой инициализацией: Соответсвенно все присваивания статичным полям поместить в этот init(). Однако, если у тебя есть несколько статических классов, ссылающихся при инициализации друг на друга - разработка обещает быть весёлой ![]() У нас в проекте существуют и статичные классы без состояния(т.е. без методов) - с ними таких проблем не возникает, и с минимальным состоянием - это статические фабрики объектов. Но у нас нет одного статического класса, которому нужна инициализация другого статического - это перебор, нельзя так активно генератор косяков под названием "статичный класс" использовать. Ещё можно у каждого статик-класса создать метод init(). И вызвать при старте приложения все init() в нужном порядке - это сделает код гораздо прозрачнее. Но все присваивания полям должны быть либо линивыми либо в коде init()! Последний раз редактировалось expl; 22.02.2012 в 23:52. |
|
|||||
|
На самом деле случайно нарвался на этот момент. У меня суть в том, что часть классов ( типа синглтон ) имеют только 1 инстанс, соотв в таких случаях я по обычке ВСЕ переменные такого класса задаю как статик или статик конст ( ну ежели и переменная не будет меняться ) при этом класс не статичный , это касается тока переменных.
А тут случайно вызвал утилитный метод отдельно и попал в просак) искал ошибку часа 1.5 ))
__________________
Марк Tween |
|
|||||
|
Цитата:
А вот если проблемы возникают с внешней либой построенной на статичных классах - опиши по-подробнее - тут придется выкручиваться по ситуации. |
|
|||||
|
Цитата:
Причём cinit это обычный метод, туда можно код понаписать: class ManagerSkin { private static var element:MovieClip = Skins.getElement(); trace("hello from cinit"); } Добавлено через 36 минут Цитата:
Если мы создадим два класса сто статическими полями и кросс ссылками друг на друга то это упадёт в рантайме т.к. во втором сините мы попробуем получить другой тип который ещё не проинитился и вместо него получим null
__________________
:) |
|
|||||
|
Т.е. что, получается если нет кросс-ссылок, а мы содим вот такую весчь:
public class A { public static var a:int = B.b; } public classB { public static var b:int = 10; } Вообще да, проверил работает, действительно предсказуемо. Но дело в том что на практике все время сталкивался с проблемами при обращении к сатитческим полям. Видимо из-за того, что неочевидно кроссылки создал. Приходилось решать ленивой инициализацией (а переполнение стека не происходило, потому что разные части класса инициализировались, наверно). Поэтому думал что он вообще как повезёт их инициализирует. Вобщем, дров наломать можно. С внутренними классами вообще всё безобразно: package { import flash.display.Sprite; public class Example extends Sprite { // Падает со словами "Inner не является конструктором." public static var INNER:Inner = new Inner(); public function Example() { trace(INNER); } } } class Inner {} package { import flash.display.Sprite; public class Example extends Sprite { private static var _INNER:Inner; public static function get INNER():Inner { if (_INNER == null) { _INNER = new Inner(); } return _INNER; } public function Example() { trace(INNER);//[object Inner] } } } class Inner {} |
![]() |
![]() |
Часовой пояс GMT +4, время: 02:54. |
|
|
« Предыдущая тема | Следующая тема » |
|
|