解决方案 »

  1.   

    service也是跑在UI Thread里的,只是比activity报ANR的阀值要大些,记得应该是>15秒报ANR,如果需要耗时的操作,还是应该放到子线程里完成。
      

  2.   

    PollingService 里面开启一个线程处理网络数据,不要用ipc bindService的方式,用广播通知数据更新。
      

  3.   

    下面是Service的代码,启动我调用actionStartPing,进入聊天页面,调用actionChatStartPing,调整 请求平率为5秒一次,但不知道为什么会出现ANR问题
    public class PollingService extends Service {  
       
        public static final String ACTION = "com.ysxj.RenHeDao.Service.PollingService";  
           
        private Notification mNotification;  
        private NotificationManager mManager;  
        
        private static int  IsCON_TIMEOUT = 0;
    private static final int  CON_TIMEOUT = 60*1000;//无网络状态重试
    private static final int  ALIVE_INTERVAL=60*1000;//正常心跳
    private static final int  ALIVE_CHATINTERVAL=5*1000;//聊天页面心跳

    private static int KEEP_ALIVE_INTERVAL=ALIVE_INTERVAL;

    private static boolean isBroadcast=false;

    private static String updatetime="";
    private SysMessageListDao sListDao;
    private ChatMessageListDao cListDao;
    private String TAG="PollingService";


    public static String MQTT_CLIENT_ID = "RenHeDao"; // These are the actions for the service (name are descriptive enough)
    private static final String ACTION_START = MQTT_CLIENT_ID + ".START";
    private static final String ACTION_STOP = MQTT_CLIENT_ID + ".STOP";
    private static final String ACTION_KEEPALIVE = MQTT_CLIENT_ID + ".KEEP_ALIVE";
    private static final String ACTION_RECONNECT = MQTT_CLIENT_ID + ".RECONNECT";
    private static final String ACTION_SEND = MQTT_CLIENT_ID + ".SEND";
    private static final String ACTION_WAITFORNETWORK = MQTT_CLIENT_ID + ".WAIT_FOR_NETWORK";
    public static  final String    ACTION_STARTKEEPALIVE=MQTT_CLIENT_ID + ".STARTKEEPALIVES";
    public static  final String    ACTION_CHATSTARTKEEPALIVE=MQTT_CLIENT_ID + ".CHATSTARTKEEPALIVES"; private Handler handler;  
       
        @Override  
        public IBinder onBind(Intent intent) {  
            return null;  
        }  
     // 发送心跳信息
      public static void actionStartPing(Context ctx) {
      isBroadcast=false;
      Intent i = new Intent(ctx, PollingService.class);
      i.setAction(ACTION_STARTKEEPALIVE);
      ctx.startService(i);
      }
      // 聊天页面发送心跳信息
      public static void actionChatStartPing(Context ctx) {
          isBroadcast=true;
      Intent i = new Intent(ctx, PollingService.class);
      i.setAction(ACTION_CHATSTARTKEEPALIVE);
      ctx.startService(i);
      }
       
        @Override  
        public void onCreate() {        Logger.v(TAG, "MyQurData===onCreate=====!");
        }  
           
          
        @Override  
        public void onStart(Intent intent, int startId) { 
           sListDao=new SysMessageListDao(PollingService.this);
             cListDao=new ChatMessageListDao(PollingService.this);
          Logger.v(TAG, "MyQurData===onStart=====!"+DateHelp.NowTime());    }  
       
        
      //启动服务接收信息
       @Override
       public int onStartCommand(Intent intent, int flags, int startId)
       {
       if (intent.getAction().equals(ACTION_STOP) == true) { //停止服务
       this.stopSelf(0);
           }else if (intent.getAction().equals(ACTION_WAITFORNETWORK) == true) { //等待网络 
        
           }else if (intent.getAction().equals(ACTION_STARTKEEPALIVE) == true) { //启动定时心跳信息
             KEEP_ALIVE_INTERVAL=ALIVE_INTERVAL;
              stopKeepAlives();
             startKeepAlives();
           } else if (intent.getAction().equals(ACTION_KEEPALIVE) == true) { //发送心跳信息
    keepAlive();

       }else if(intent.getAction().equals(ACTION_CHATSTARTKEEPALIVE) == true)
           {
             KEEP_ALIVE_INTERVAL=ALIVE_CHATINTERVAL; 
            stopKeepAlives();
            startKeepAlives();
           }
       return startId;
          }  private synchronized void keepAlive() {
     Logger.v(TAG, "keepAlive=====!"+DateHelp.NowTime());
     MyQurData(MyApplication.getInstance().getUpdatetime());

      }// Schedule application level keep-alives using the AlarmManager设置定时发送心跳信息
      private synchronized void startKeepAlives() {
       Logger.v(TAG, "MyQurData===startKeepAlives=====!"+DateHelp.NowTime());  Intent  i = new Intent();
      i.setClass(this, PollingService.class);
      i.setAction(ACTION_KEEPALIVE);
      //startService(i);
      long triggerAtTime = SystemClock.elapsedRealtime();
      PendingIntent pi = PendingIntent.getService(this, 0, i, PendingIntent.FLAG_UPDATE_CURRENT);
      AlarmManager alarmMgr = (AlarmManager)getSystemService(Context.ALARM_SERVICE);
      alarmMgr.setRepeating(AlarmManager.ELAPSED_REALTIME,triggerAtTime+KEEP_ALIVE_INTERVAL,KEEP_ALIVE_INTERVAL, pi);
      }
      
     
      //停止轮询服务  
      private synchronized void stopKeepAlives() {  
     
      Intent  i = new Intent();
      i.setClass(this, PollingService.class);
      i.setAction(ACTION_KEEPALIVE);
      //startService(i);
      long triggerAtTime = SystemClock.elapsedRealtime();
      PendingIntent pi = PendingIntent.getService(this, 0, i, PendingIntent.FLAG_UPDATE_CURRENT);
      AlarmManager alarmMgr = (AlarmManager)getSystemService(Context.ALARM_SERVICE);
            //取消正在执行的服务  
      alarmMgr.cancel(pi);  
        }  
           
        @Override  
        public void onDestroy() {  
            super.onDestroy();  
            System.out.println("Service:onDestroy");  
        }  
        private void MyQurData(String updatetime){    
         AsyncHttpRestClient.get(ChatAPI.DynamicNewsListURL(updatetime), jHandler);
        }
      

  4.   

    我已经自己解决了,问题出在onStartCommand方法中