2015-03-13 2 views
0

Я использую Android Studio (intelliJ-idea) для разработки Android. Я получаю предупреждение за этот кусок кода:Многопоточная Java - синхронизация - предупреждение Android Studio

if (status == STATUS_SOLVING) { 
     if (!solverThread.isAlive()) 
      if (status != STATUS_SOLVED) // <<<<<< WARNING THIS LINE 
       status = STATUS_DATA_COLLECTING; 
    } 

линия указано выше, дает мне предупреждение о том, что это условие всегда истинно. Я могу понять, почему это верно, если вся программа работает в одном потоке.

Но поскольку моя программа использует параллельный поток для изменения значения status, не означает ли это, что это условие может измениться между строкой # 1 и # 3 в фрагменте выше?

Действительно ли это предупреждение? Я что-то упускаю?

Что-то изменится, если я ввожу вложенные ifs в один сингл, если с оператором &&?

ответ

1

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

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

+0

Спасибо! Можете ли вы также рассмотреть ответ на вторую часть? Замена вложенных if с помощью оператора &&. – Kasra

+0

Не изменится, компилятор будет оптимизировать в любом случае - если переменная нестабильна, и в этом случае она будет каждый раз загружать свое значение из ОЗУ. В общем, это действительно опасный код, хотя я могу видеть 3 или 4 условия гонки только во фрагменте, который вы мне дали. Если у вас нет опыта работы с многопоточными и гоночными условиями, я предлагаю получить обзор кода у кого-то, кто это делает. –

+0

Это был просто эксперимент ... Я планировал использовать объекты блокировки (синхронизация (блокировка)). Я считаю, что это решение для этой конкретной проблемы, поскольку я изменяю «статус» на основе полученных значений «статус», поэтому я заблокирую этот сегмент кода. Но в любом случае, спасибо за разъяснения в отношении предупреждения и оптимизации байт-кода. – Kasra

0

Если задействован второй поток и изменяет статус, то, безусловно, значение может меняться между строками 1 и 3. Тем более, что у вас нет какой-либо синхронизации потоков на месте, преднамеренной или нет. Конечно, код кажется немного небезопасным, потому что у вас обычно нет двух потоков, обращающихся к одной и той же переменной без какого-либо контроля параллелизма. Но это спекуляция, так как я не вижу остальную часть вашего кода.

В любом случае, это предупреждение, а не ошибка. Иногда предупреждения ошибочны, поэтому их можно подавить.

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

Смежные вопросы