Codename One и ключевое слово Java synchronized

У меня было подозрение, что ошибка в одном из моих проектов Codename One была вызвана одновременным выполнением одного и того же слушателя (если пользователь нажимает кнопку очень быстро несколько раз, вызывая свой слушатель до того, как он завершит выполнение) ... Я добавил в код блокирующую переменную, чтобы избежать одновременного выполнения нескольких операций, и это устранило ошибку.

Я впервые сталкиваюсь с подобной проблемой. Читая в Интернете, предлагается использовать ключевое слово synchronized Java (однако я не уверен, может ли оно быть полезным в этом случае).

У меня вопрос, поддерживается ли ключевое слово synchronized Java в Codename One.


person Francesco Galgani    schedule 01.10.2018    source источник


Ответы (2)


synchronized отлично работает в Codename One, но если вы использовали прослушиватель действий, маловероятно, что он решил проблему, если только у нас не будет огромной невообразимой ошибки.

Все события, краски, методы жизненного цикла и т. Д. Вызываются в EDT. Это один поток, поэтому два щелчка по кнопке будут происходить в одном потоке. synchronized было бы бессмысленным. EDT используется от взаимодействия с сенсорным экраном до события в самом компоненте, и вы можете проверить это с помощью метода isEDT().

Более вероятен сценарий, когда один из прослушивателей действий на кнопке использует invokeAndBlock, что может вызвать странные побочные эффекты в цепочке отправки событий. invokeAndBlock() используется внутри AndWait методами, диалогами и т. Д.

person Shai Almog    schedule 01.10.2018
comment
Большое спасибо за интересный и проясняющий ответ. Я был сбит с толку, потому что думал, что ActionListener выполняется в отдельном потоке. Возможно, я нашел истинную причину ошибки: использование animateUnlayout (который возвращается немедленно, позволяя запускать другое выполнение того же слушателя, не дожидаясь окончания анимации) вместо animateUnlayoutAndWait (что предотвращает выполнение другого слушателя до окончания анимации) . В случае animateUnlayout анимация выполняется внутри или вне EDT? Я спрашиваю об этом, потому что он немедленно возвращается. - person Francesco Galgani; 01.10.2018
comment
Обе анимации выполняются на 100% на EDT. Анимация просто включает флаг, который заставляет анимацию запускаться для каждого цикла EDT (тик AKA). Метод AndWait использует invokeAndBlock для открытия потока, который только ожидает (больше ничего не делает). invokeAndBlock берет EDT и поддерживает его в рабочем состоянии, но строки сразу после них не появляются, потому что они уже находятся в середине выполнения. Итак, как только invokeAndBlock закончит, следующая строка (и следующие события в цепочке) будут выполнены. - person Shai Almog; 02.10.2018
comment
Например. если у Button есть 3 слушателя, а у слушателя 2 10 строк. В строке 5 используется метод AndWait. все строки после строки 5 не будут выполняться, как и прослушиватель 3. После того, как AndWait истечет, будут вызваны остальные строки и прослушиватель 3 - person Shai Almog; 02.10.2018

Использование syncronized предотвратит одновременное выполнение метода, но по существу поставит в очередь выполняемый запрос, заставляя потоки ждать любого текущего выполнения.

При обработке этого сценария вы можете захотеть заблокировать нажатие кнопки, предотвратив взаимодействие с пользователем в течение некоторого периода после его первого нажатия, или на время результирующего вычисления, отключив кнопку и повторно включив ее.

person bradm6s    schedule 01.10.2018
comment
Спасибо за ответ, но я отклонил его, потому что это общий ответ, который не нацелен на Codename One и может сбивать с толку. - person Francesco Galgani; 01.10.2018