美文网首页
定时任务

定时任务

作者: 俗人浮生 | 来源:发表于2019-03-11 21:39 被阅读0次

    Android中执行定时任务也是很常见的需求,今天我们就来实现一个最简单的定时任务:从1到10每隔1秒进行数数,实现方案有:(1)Handler (2)Timer (3)RxJava(4)ExecutorService(5)Alarm,直接上代码

    /**
     * 定时任务
     */
    public class MyTimerTask {
    
        private static Long count=0L;
    
        public static void useHandler(){
            LogUtil.loge("使用Handler");
            final HandlerThread handlerThread=new HandlerThread("myThread");
            handlerThread.start();
            final Handler handler=new Handler(handlerThread.getLooper());
            //final Handler handler=new Handler();
            handler.postDelayed(new Runnable() {
                @Override
                public void run() {
                    if(count<10){
                        count++;
                        LogUtil.loge("count: " + count);
                        handler.postDelayed(this,1000);
                    }else {
                        LogUtil.loge("当前线程:"+Thread.currentThread().getName());
                        handlerThread.quit();//释放Looper//停止任务
                    }
                }
            },1000);
        }
    
        public static void useTimer(){
            LogUtil.loge("使用Timer");
            final Timer timer=new Timer();
            TimerTask timerTask=new TimerTask() {
                @Override
                public void run() {
                    if(count<10){
                        count++;
                        LogUtil.loge("count: " + count);
                    }else {
                        //LogUtil.loge("如果要开始下一轮任务,会报错的");
                        //timer.schedule(this,1000,2000);//执行同一个TimerTask不行
                        timer.cancel();//停止任务
                    }
                }
            };
            timer.schedule(timerTask,3000,1000);
            //执行新的TimerTask可以
            timer.schedule(new TimerTask() {
                @Override
                public void run() {
                    LogUtil.loge("执行新任务完毕!");
                }
            },6000);
        }
    
        public static void useExecutorService(){
            final ScheduledExecutorService scheduledExecutorService = Executors.newScheduledThreadPool(1);
            scheduledExecutorService.scheduleAtFixedRate(new Runnable() {
                @Override
                public void run() {
                    if(count<10){
                        count++;
                        LogUtil.loge("count: " + count);
                    }else {
                        scheduledExecutorService.shutdown();//关闭线程池
                    }
                }
            },0,1,TimeUnit.SECONDS);
        }
        
        public static void useRxJava1(){
            LogUtil.loge("使用RxJava");
             Disposable disposable = Observable.intervalRange(0, 10, 5, 1, TimeUnit.SECONDS)
                    .map(new Function<Long, Long>() {
                        @Override
                        public Long apply(Long aLong) throws Exception {
                            return aLong + 1;
                        }
                    })
                    .subscribe(new Consumer<Long>() {
                        @Override
                        public void accept(Long count) throws Exception {
                            LogUtil.loge("count: " + count);
                        }
                    });
            //disposable.dispose();//停止任务
        }
    
        public static void useRxJava2(){
            LogUtil.loge("使用RxJava");
            final CompositeDisposable compositeDisposable=new CompositeDisposable();
            Observable.create(new ObservableOnSubscribe<Long>() {
                @Override
                public void subscribe(ObservableEmitter<Long> emitter) throws Exception {
                    if (emitter.isDisposed()||count==10) {
                        return;
                    }
                    emitter.onNext(++count);
                    emitter.onComplete();
                }
            }).delay(1,TimeUnit.SECONDS,true)// 设置delayError为true,表示出现错误的时候也需要延迟进行通知,达到无论是请求正常还是请求失败,都是1s后重新订阅,即重新请求。
            .repeat()// repeat保证请求成功后能够重新订阅
            .retry() // retry保证请求失败后能重新订阅
            .subscribe(new Observer<Long>() {
                @Override
                public void onSubscribe(Disposable d) {
                    compositeDisposable.add(d);
                }
    
                @Override
                public void onNext(Long aLong) {
                    LogUtil.loge("count: " + aLong);
                }
    
                @Override
                public void onError(Throwable e) {
    
                }
    
                @Override
                public void onComplete() {
    
                }
            });
            //compositeDisposable.clear();//停止任务
    
        }
    
    }
    

    之所以写这一篇,也是因为两次面试中都被问到了,一次是问了Timer相关的,说真的之前Timer用得不多,有点懵。说到Timer,请注意一下上面笔者中注释掉的代码,运行会报以下异常:

    java.lang.IllegalStateException: TimerTask is scheduled already

    所以,对于Timer来说,它不能重复执行某任务,若在某个任务执行/取消之后,再次执行则会抛出一个IllegalStateException异常。
    Timer相关的知识详情请参考:
    https://www.cnblogs.com/benhero/p/4521727.html
    https://www.cnblogs.com/xiaotaoqi/p/6874713.html

    另一次是问了一个自定义控件中的定时任务,我说用Handler实现的,然而面试官问为什么不用RxJava呢?那会我才知道,原来RxJava也可以用来做定时任务,请原谅我一直用RxJava只是单纯滴与Retrofit配合使用而已,其实RxJava功能很是强悍,N多个操作符可供使用,详情可参考:
    http://www.jcodecraeer.com/a/chengxusheji/java/2017/0731/8315.html

    相关文章

      网友评论

          本文标题:定时任务

          本文链接:https://www.haomeiwen.com/subject/rpxvpqtx.html