Activity


public class MainActivity extends ListActivity {
    private int intentNumber = 0;
    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        List<String> mData = new ArrayList<String>(Arrays.asList("启动一个新的工作线程", "启动一个前台服务", //
                "设置一次性定时后台服务", "设置一个周期性执行的定时服务", "取消AlarmManager的定时服务"));
        ListAdapter mAdapter = new ArrayAdapter<String>(this, android.R.layout.simple_list_item_1, mData);
        setListAdapter(mAdapter);
    }
    @Override
    protected void onListItemClick(ListView l, View v, int position, long id) {
        switch (position) {
        case 0:
            intentNumber++;
            Intent intent = new Intent(this, MyIntentService.class);
            Bundle bundle = new Bundle();
            bundle.putInt("intentNumber", intentNumber);
            intent.putExtras(bundle);
            startService(intent);//每次启动都会新建一个工作线程,但始终只有一个IntentService实例
            break;
        case 1:
            startService(new Intent(this, ForegroundService.class));
            break;
        case 2:
            Intent intent2 = new Intent(this, LongRunningService.class);
            intent2.putExtra("type", "onceAlarm");
            startService(intent2);
            break;
        case 3:
            Intent intent3 = new Intent(this, LongRunningService.class);
            intent3.putExtra("type", "repeatAlarm");
            startService(intent3);
            break;
        case 4:
            ((AlarmManager) getSystemService(ALARM_SERVICE)).cancel(PendingIntent.getBroadcast(this, 0, new Intent(this, AlarmReceiver.class), 0));
            break;
        }
    }
}

IntentService

/** 所有请求的Intent记录会按顺序加入到【队列】中并按顺序【异步】执行,并且每次只会执行【一个】工作线程,当所有任务执行完后IntentService会【自动】停止 */
public class MyIntentService extends IntentService {
    public MyIntentService() { //必须实现父类的构造方法  
        super("MyIntentService");
    }
    @Override
    protected void onHandleIntent(Intent intent) {//注意,因为这里是异步操作,所以这里不能直接使用Toast。
        int intentNumber = intent.getExtras().getInt("intentNumber");//根据Intent中携带的参数不同执行不同的任务
        Log.i("bqt", "第" + intentNumber + "个工作线程启动了");
        try {
            Thread.sleep(3000);
        } catch (InterruptedException e) {
            e.printStackTrace();
        }
        Log.i("bqt", "第" + intentNumber + "个工作线程完成了");
    }
    @Override
    public IBinder onBind(Intent intent) {
        Log.i("bqt", "onBind");
        return super.onBind(intent);
    }
    @Override
    public void onCreate() {
        Log.i("bqt", "onCreate");
        super.onCreate();
    }
    @Override
    public int onStartCommand(Intent intent, int flags, int startId) {
        Log.i("bqt", "onStartCommand");
        return super.onStartCommand(intent, flags, startId);
    }
    @Override
    public void setIntentRedelivery(boolean enabled) {
        super.setIntentRedelivery(enabled);
        Log.i("bqt", "setIntentRedelivery");
    }
    @Override
    public void onDestroy() {
        Log.i("bqt", "onDestroy");
        super.onDestroy();
    }
}

前台服务

/**所谓的前台服务就是状态栏显示的Notification,可以让Service没那么容易被系统杀死  */
public class ForegroundService extends Service {
    @Override
    public IBinder onBind(Intent intent) {
        return null;
    }
    @Override
    public void onCreate() {
        super.onCreate();
        Notification.Builder localBuilder = new Notification.Builder(this).setContentIntent(PendingIntent.getActivity(this, 0, new Intent(this, MainActivity.class), 0))
                .setAutoCancel(false).setSmallIcon(R.drawable.ic_launcher).setTicker("Foreground Service Start").setContentTitle("前台服务").setContentText("正在运行...");
        startForeground(1, localBuilder.build());
    }
    @Override
    public void onDestroy() {
        Log.i("bqt", "onDestroy");
        super.onDestroy();
    }
}

定时后台服务

public class LongRunningService extends Service {
    public static final int anHour = 3 * 1000;//设置每隔3秒钟打印一次时间
    @Override
    public IBinder onBind(Intent intent) {
        return null;
    }
    @Override
    public int onStartCommand(Intent intent, int flags, int startId) {
        //定时任务为:发送一条广播。在收到广播后启动本服务,本服务启动后又发送一条广播……
        PendingIntent pendingIntent = PendingIntent.getBroadcast(this, 0, new Intent(this, AlarmReceiver.class), 0);
        //使用【警报、闹铃】服务设置定时任务。CPU一旦休眠(比如关机状态),Timer中的定时任务就无法运行;而Alarm具有唤醒CPU的功能。
        AlarmManager manager = (AlarmManager) getSystemService(ALARM_SERVICE);
        long triggerAtTime;//闹钟(首次)执行时间
        String type = intent.getStringExtra("type");
        if ("onceAlarm".equals(type)) {//)//设置在triggerAtTime时间启动由operation参数指定的组件。该方法用于设置一次性闹钟
            triggerAtTime = SystemClock.elapsedRealtime() + anHour;//相对于系统启动时间,Returns milliseconds since boot, including time spent in sleep.
            manager.set(AlarmManager.ELAPSED_REALTIME_WAKEUP, triggerAtTime, pendingIntent);
        } else if ("repeatAlarm".equals(type)) {//设置一个周期性执行的定时服务,参数表示首次执行时间和间隔时间
            triggerAtTime = System.currentTimeMillis() + anHour;//相对于1970……绝对时间,Returns milliseconds since boot, including time spent in sleep.
            manager.setRepeating(AlarmManager.RTC_WAKEUP, triggerAtTime, anHour, pendingIntent);
        } else if ("work".equals(type)) {
            //开辟一条线程,用来执行具体的定时逻辑操作
            new Thread(new Runnable() {
                @Override
                public void run() {
                    Log.i("bqt", new SimpleDateFormat("yyyy.MM.dd HH-mm-ss", Locale.getDefault()).format(new Date()));
                }
            }).start();
        }
        /**type有五个可选值: 
        AlarmManager.ELAPSED_REALTIME  闹钟在睡眠状态下不可用,如果在系统休眠时闹钟触发,它将不会被传递,直到下一次设备唤醒;使用相对系统启动开始的时间
        AlarmManager.ELAPSED_REALTIME_WAKEUP  闹钟在手机睡眠状态下会唤醒系统并执行提示功能,使用相对时间
        AlarmManager.RTC  闹钟在睡眠状态下不可用,该状态下闹钟使用绝对时间,即当前系统时间
        AlarmManager.RTC_WAKEUP  表示闹钟在睡眠状态下会唤醒系统并执行提示功能,使用绝对时间
        AlarmManager.POWER_OFF_WAKEUP  表示闹钟在手机【关机】状态下也能正常进行提示功能,用绝对时间,但某些版本并不支持! */
        return super.onStartCommand(intent, flags, startId);
    }
}

广播接收者

public class AlarmReceiver extends BroadcastReceiver {
    @Override
    public void onReceive(Context context, Intent intent) {
        Toast.makeText(context, "定时任务已经执行了", Toast.LENGTH_SHORT).show();
        Intent workIntent = new Intent(context, LongRunningService.class);
        workIntent.putExtra("type", "work");
        context.startService(workIntent);
    }
}

清单文件

<?xml version="1.0" encoding="utf-8"?>
<manifest xmlns:android="http://schemas.android.com/apk/res/android"
    package="com.bqt.intentservice"
    android:versionCode="1"
    android:versionName="1.0" >
    <uses-sdk
        android:minSdkVersion="17"
        android:targetSdkVersion="21" />
    <application
        android:allowBackup="true"
        android:icon="@drawable/ic_launcher"
        android:label="@string/app_name"
        android:theme="@style/AppTheme" >
        <activity
            android:name=".MainActivity"
            android:label="@string/app_name" >
            <intent-filter>
                <action android:name="android.intent.action.MAIN" />
                <category android:name="android.intent.category.LAUNCHER" />
            </intent-filter>
        </activity>
        <service
            android:name=".MyIntentService"
            android:exported="false" >
            <intent-filter>
                <action android:name="com.test.intentservice" />
            </intent-filter>
        </service>
        <service android:name=".ForegroundService" />
        <service android:name=".LongRunningService" />
        <receiver android:name=".AlarmReceiver" />
    </application>
</manifest>

服务 IntentService 前台服务 定时后台服务的更多相关文章

  1. .NET 使用自带 DI 批量注入服务(Service)和 后台服务(BackgroundService)

    今天教大家如何在asp .net core 和 .net 控制台程序中 批量注入服务和 BackgroundService 后台服务 在默认的 .net 项目中如果我们注入一个服务或者后台服务,常规的 ...

  2. Android : App客户端与后台服务的AIDL通信以及后台服务的JNI接口实现

    一.APP客户端进程与后台服务进程的AIDL通信 AIDL(Android Interface definition language-“接口定义语言”) 是 Android 提供的一种进程间通信 ( ...

  3. CentOS后台服务管理类

    目录 一.service 后台服务管理(临时,只对当前有效) 二.chkconfig 设置后台服务的自启配置(永久) 三.CentOS7 后添加的命令:systemctl 一.service 后台服务 ...

  4. 答CsdnBlogger问-关于定时和后台服务问题

    本文来自http://blog.csdn.net/liuxian13183/ ,引用必须注明出处! 前段时间写了不少博客,在问答页面也陆续回答几十个问题,之后Csdn乙同学找到我,说要推荐我参加问答类 ...

  5. Android Services (后台服务)

    一.简介 服务是可以在后台执行长时间运行的应用程序组件,它不提供用户界面. 另一个应用程序组件可以启动一个服务,并且即使用户切换到另一个应用程序,它仍然在后台运行. 另外,组件可以绑定到一个服务来与它 ...

  6. Android 三级联动选择城市+后台服务加载数据库

    技术渣,大家将就着看 首先我们需要一个xml数据保存到数据库,这里我从QQ下面找到一个loclist.xml文件 <CountryRegion Name="中国" Code= ...

  7. highchart访问一次后台服务返回多张图表数据

    本文承接上一篇,我们制作动态图表的时候,往往需要的不止一张图表,如果每张图表都与服务接口做一次交互的话未免太过频繁,这无论对前后还是后台都是一种压力,本文介绍一种一次访问返回多组数据的方式来减少前台与 ...

  8. Android之后台服务判断本应用Activity是否处于栈顶

    在Android开发中,我们经常想知道是否自己的服务处于后台运行中,因为在后台运行的服务器优先级会降低,也就极有可能会被系统给回收掉,有什么好办法呢?Google推荐我们将服务运行到前台,如何知道服务 ...

  9. .NET Core 中的通用主机和后台服务

    简介 我们在做项目的时候, 往往要处理一些后台的任务. 一般是两种, 一种是不停的运行,比如消息队列的消费者.另一种是定时任务. 在.NET Framework + Windows环境里, 我们一般会 ...

随机推荐

  1. php魔法常量

    有七个魔术常量它们的值随着它们在代码中的位置改变而改变.例如 __LINE__ 的值就依赖于它在脚本中所处的行来决定.这些特殊的常量不区分大小写,如下: 名称 说明 __LINE__ 文件中的当前行号 ...

  2. DBA优化SQL采用的WITH AS 用法简介

    一.WITH AS简介 WITH AS的用法从oracle 9i新增的,官方文档也称之为:subquery factoring;在进行复杂的查询.统计等操作时使用with as 子句可以大大提高性能! ...

  3. WordPress社会化评论插件多说、有言、灯鹭、评论啦

    社会化登录是指网站的用户通过使用QQ.人人网.腾讯微博.新浪微博等社会化媒体账号登录该网站,并让用户能够使用社会化媒体账号进行允许的操作,如评论.分享等.经过简单的代码整合,社会化媒体账号可以在第三方 ...

  4. php 被抛弃使用的函数

    call_user_method()(使用 call_user_func() 替代)     call_user_method_array() (使用 call_user_func_array() 替 ...

  5. java-map-EnumMap

    在平常的项目中,enumMap是比较少用到的一种map,一般都不会使用到这种容器,那么我将从如下几个方面来阐述我对enumMap的理解 1.使用场景 在key是比较固定的情况下,使用enumMap是最 ...

  6. 【GoLang】golang 微服务框架 go-kit

    golang-Microservice Go kit - A toolkit for microservices kubernetes go-kit_百度搜索 Peter Bourgon谈使用Go和& ...

  7. mysql 日期比较

    情景是:距离当前到期时间多少天 可以考虑当前系统时间加上某个天数后,与数据库的字段作比较 1.已知的时间>=CURDATE()+10 2.在数据的查询中,考虑到sql语句的优化问题,应减少通配符 ...

  8. 转: pthread_create()

    pthread_create函数 原型:int  pthread_create((pthread_t  *thread,  pthread_attr_t  *attr,  void  *(*start ...

  9. 转:VC中WORD,DWORD,unsigned long,unsigned short的区别(转)

    typedef unsigned long       DWORD;typedef int                 BOOL;typedef unsigned char       BYTE; ...

  10. Entity Framework with MySQL 学习笔记一(拦截)

    参考 : http://msdn.microsoft.com/en-us/data/dn469464.aspx EF 允许我们在发送SQL请求和返回数据时做一些拦截的动作 比如可以自定义写 log , ...