Как зациклить услугу? - PullRequest
       0

Как зациклить услугу?

13 голосов
/ 19 августа 2011

Мой сервис должен проверять что-то каждую минуту и ​​

while(true)
{
   Thread.sleep(60000) 
   //REST OF CODE HERE//
}

не работает. Зависание приложения и его принудительное прекращение.

Я уверен, что проблема в цикле while, но я подумал, что это был единственный способ бесконечно повторять сервис всякий раз, когда выполняется метод onStart ().

Любые предложения приветствуются.

EDIT

Я исправил это, и на случай, если вам интересно, как выглядит код, вот так:

@Override
public void onStart(Intent intent, int startId) {
    // TODO Auto-generated method stub
    super.onStart(intent, startId);
    Toast.makeText(this, "Service running", Toast.LENGTH_SHORT).show();

    handler = new Handler(){

        @Override
        public void handleMessage(Message msg) {
            // TODO Auto-generated method stub
            super.handleMessage(msg);
            Toast.makeText(protectionService.this, "5 secs has passed", Toast.LENGTH_SHORT).show();
        }

    };



    new Thread(new Runnable(){
        public void run() {
        // TODO Auto-generated method stub
        while(true)
        {
           try {
            Thread.sleep(5000);
            handler.sendEmptyMessage(0);

        } catch (InterruptedException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        } 

        }

                        }
    }).start();
}

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

Я хотел бы поблагодарить vineetska, Janusz и inazaruk за предложение использовать Handlers. Я хотел бы поблагодарить всех, кто также ответил, ваша помощь была высоко оценена.

Ответы [ 5 ]

14 голосов
/ 19 августа 2011

создайте поток в вашем сервисе и поместите цикл while следующим образом:

 new Thread(new Runnable(){
    public void run() {
    // TODO Auto-generated method stub
    while(true)
    {
       Thread.sleep(60000) 
       //REST OF CODE HERE//
    }

                    }
}).start();
5 голосов
/ 19 августа 2011

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

В вашем случае, однако, вам следует рассмотреть возможность использования AlarmManager. Он очень хорошо обрабатывает повторяющиеся события и был специально разработан для подобных сценариев.

Другим решением будет использование Handler и его функции postDelayed(). Это может использоваться, когда ваша операция (которая должна выполняться каждые 60 секунд) не занимает много времени (или в противном случае вы все равно должны запускать ее в фоновом потоке).

В целом, создание потока, который постоянно спит не является хорошим решением для мобильных устройств. Это потребляет ресурсы, которые могли быть потрачены на что-то более полезное. Особенно учитывая богатый набор возможностей Android для повторяющихся событий.

2 голосов
/ 19 августа 2011

Службы запускаются в основном потоке.Если вы хотите снять нагрузку с обработки, вам нужно запустить отдельный поток.Посмотрите на IntentService , он делает это по умолчанию.С другой стороны, бесконечно работающий сервис с sleep () может быть не очень хорошей идеей.Для обработки по расписанию вы можете использовать AlarmManager .

2 голосов
/ 19 августа 2011

Сам сервис не является субпотоком. Это означает, что каждый код, который выполняется в вашем сервисе, будет выполняться в основном потоке пользовательского интерфейса. Вам нужно запустить поток или использовать AsyncTask в вашем сервисе, чтобы переместить вычисления в фоновый режим.

Для получения дополнительной информации ознакомьтесь с документацией службы.

Если вы хотите повторять какой-то код каждую минуту, вы можете использовать обработчик .

В обработчике есть метод с именем postDelayed , который позволяет указать время, по истечении которого будет выполняться исполняемый файл. Просто снова вызовите метод в конце вашего runnable для повторного запуска кода через минуту.

0 голосов
/ 01 октября 2017

Как писал Януш, вы можете использовать обработчик для отправки сообщений с задержкой.Вот пример:

final Handler handler = new Handler();
Runnable runnable = new Runnable() {
    @Override
    public void run() {
        // Do repeatable stuff
        handler.postDelayed(this, DELAYED_TIME);
    }
};
handler.post(runnable);

Он запустит работоспособный, а затем отправит его снова и снова после DELAYED_TIME.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...