3

この質問は、優れたプログラムを作成する方法に関するより哲学的な質問と、バッテリーとシステムリソースを保護する方法に関する事実に基づく質問との間のバランスをとる行為のようなものです。具体的には、必要なタスクを実行するために、電話のバックグラウンドで永続的に実行する必要があるAndroidサービスについてです。

私の場合、バックグラウンドでいくつかのサービスを実行しています。電話がWiFiに接続されているかどうかをスキャンし、接続されている場合は変数を設定し、場所を確認して、十分に正確な場所が見つかった場合は場所を更新します。近接センサーを確認し、ノイズレベルを分析します。 RSSフィードをチェックして更新を確認します...

アプリにはいくつかの問題があり、それらはこの設計上の決定に起因する可能性があると思います。ほとんどの場合(SensorEventListenerを介して更新を提供するロケーションサービスと近接センサーを除く)、すべてのサービスのアーキテクチャは次のようになります。

public class ArchetypicalService extends Service
{
Checker checker;

public SharedPreferences prefs;
public final static String PREFS = Constants.PREFS;

@Override
public IBinder onBind(Intent intent) 
{
    return null;
}

@Override
public void onCreate() 
{
    prefs = getSharedPreferences(PREFS, 0);
}

@Override
public int onStartCommand(Intent intent, int flags, int startId) 
{
    checker = new Checker();
    checker.run();
    return START_STICKY;
}

@Override
public void onDestroy() 
{
    super.onDestroy();
}

private class Checker implements Runnable
{
    private Handler handler = new Handler();
    public static final int checkingDelay = 1000; // this number varies depending on what purpose this service has
    @Override
    public void run() 
    {
        //what happends here depends on what the service does
        handler.postDelayed(this, checkingDelay);
    }
}
}

アプリの起動時にサービスが開始されます。このような:

Intent intent = new Intent(this,ArchetypicalService.class);
startService(intent);

START_STICKYのおかげで、アクティビティを停止してもサービスは実行され続けます。これは私が書いたときはすべて教科書のように見えましたが、Androidを使用すればするほど、永続的に実行されるサービスを実装すべきではないと言うブログエントリに出くわします。それらが悪いスタイルである以上に、アプリがクラッシュしてバッテリーと電話リソースを使い果たす可能性が高くなります。これはすべて正しいかもしれません:私のアプリはたくさんクラッシュし、バッテリーを使い果たします。

だから、私の質問は、センサースイープやインターネット上のデータのチェックなどの機能をバックグラウンドで定期的に実行する必要がある場合、すべてのアクティビティが閉じられていても、それを実装するためのより良い方法はありますか?(そして私はすべての答えやアイデアを歓迎しますが、いくつかの有用なサンプルコードをさらに提供するものを歓迎します)

4

2 に答える 2

4

センサーのスイープやインターネット上のデータのチェックなどの機能をバックグラウンドで定期的に実行する必要がある場合、すべてのアクティビティが閉じられていても、それを実装するためのより良い方法はありますか?

AlarmManager作業が定期的に発生するようにスケジュールするために使用します。

たとえば、「RSS フィードの更新をチェックする」とします。RSS フィードを再度チェックする時が来るまで時間が経過するのを待って、サービスをメモリに保持し、その仮想親指をいじくり回すのはばかげています。他のプラットフォームでは、cronまたは Windows スケジュール タスクのようなものを使用します。Android では、同等のものはAlarmManager.

フローが「作業を行い、一定時間待機し、作業を行い、一定時間待機し、...」であるほとんどすべての状況は、 と を使用AlarmManagerして実装する必要がありIntentServiceます。後者はバックグラウンド スレッドを提供し、自動的に作業が完了したらシャットダウンします。この方法では、ユーザーに積極的に価値を提供しているときにのみ RAM を消費します。

于 2012-10-17T12:41:03.047 に答える
1

http://developer.android.com/guide/components/services.html。サービスは個別のスレッドを作成しません。長時間実行される操作の場合は、スレッドで実行する必要があります。したがって、多くのサービスがある場合、メインUIスレッドですべてを実行するとメモリが消費されます。必ずスレッドで実行してください。アプリのクラッシュの問題を解決する可能性があります。このリンクも確認してください。5秒ごとにページをリクエストし続け、バッテリーを消耗させないようにするにはどうすればよいですか?

于 2012-10-17T11:23:48.317 に答える