2011-06-02 38 views
1

我正在研究任务调度器应用程序作为我的大学项目,我有一个服务来检查任务的过期时间。我实施了处理程序来检查到期时间。当应用程序的到期时间与当前时间匹配时,它会发送状态栏通知。在这一点上,我暂停使用Thread.sleep方法的线程一分钟,这导致我的应用程序挂起。在logcat中,它显示了应用程序对CPU的大量使用。Thread.sleep使得程序挂起?

我正在从数据库中获取数据,但是当Thread.sleep未被调用时,它工作正常。 请帮忙。

下面是代码:

package com.apps.niit.taskm; 
import java.util.ArrayList; 
import java.util.Calendar; 

import android.app.Notification; 
import android.app.NotificationManager; 
import android.app.PendingIntent; 
import android.app.Service; 
import android.content.Context; 
import android.content.Intent; 
import android.os.Bundle; 
import android.os.Handler; 
import android.os.IBinder; 
import android.util.Log; 


public class ExpireTimeService extends Service { 

    DataHelper dh; 
    ArrayList<String> tData=new ArrayList<String>(); 
    String date; 
    Calendar c; 
    String str; 
    String str1; 
    String str2; 
    String str3; 
    String str4; 
    String str5; 
    int notificationID=1; 
    String [][] data; 
    NotificationManager notificationManager; 
    @Override 
    public IBinder onBind(Intent arg0) { 
     // TODO Auto-generated method stub 
     return null; 
    } 
    @Override 
    public void onCreate(){ 
     super.onCreate(); 
     dh = new DataHelper(this); 
     fetchData(); 
     handler.removeCallbacks(updateTimeTask); 
     handler.postDelayed(updateTimeTask, 1000); 
    } 
    public void fetchData(){ 
     String eDate = android.text.format.DateFormat.format("d/M/yyyy", new java.util.Date()).toString(); 
     tData.addAll(this.dh.selectDate(eDate)); 
     data =new String[tData.size()][4]; 
     if(!tData.isEmpty()){ 
      for(int i=0; i<tData.size();i++){ 
       breakString(tData.get(i)); 
       data[i][0]=str1; 
       data[i][1]=str2; 
       data[i][2]=str3; 
       data[i][3]=str4; 
      } 
     } 
    } 

    public void stopService(){ 
     stopSelf(); 
    } 
    private Runnable updateTimeTask = new Runnable() { 
     public void run(){ 
      try { 
       String time = android.text.format.DateFormat.format("k:m", new java.util.Date()).toString(); 

       for(int i=0; i<tData.size();i++){ 
        if(data[i][3].equals(time)){ 
        //send notification code goes here 
         String serName = Context.NOTIFICATION_SERVICE; 
         notificationManager = (NotificationManager)getSystemService(serName);    
         String ticker= data[i][0]+" "+data[i][1]+" "+data[i][2]+" "+data[i][3]; 
         long when= System.currentTimeMillis(); 
         int icon = R.drawable.icon; 
         Notification notification = new Notification(icon, ticker,when); 
         Intent intent = new Intent (getApplicationContext(), DisplayTask.class); 
         Bundle myBundle = new Bundle();  
         myBundle.putString("str1", data[i][0]); 
         myBundle.putString("str2", data[i][1]);Log.i("data1",data[i][1]); 
         myBundle.putString("str3", data[i][2]);Log.i("data1",data[i][2]); 
         myBundle.putString("str4", data[i][3]);Log.i("data1",data[i][3]); 
         intent.putExtras(myBundle); 
         PendingIntent launchIntent = PendingIntent.getActivity(getApplicationContext(), 0, intent, 0); 
         notification.setLatestEventInfo(getApplicationContext(), "", "", launchIntent); 
         notificationID=1; 
         notificationManager.notify(notificationID, notification); 
         Thread.sleep(10000);      
        } 
       } 
       handler.postDelayed(this, 1000); 
      } catch (Exception e) { 
       // TODO Auto-generated catch block 
       Log.e("Error from service", e.toString()); 
      } 
     }  
    }; 

    private void breakString(String str) { 
     // TODO Auto-generated method stub 
     str1 = str.substring(0, str.indexOf(";")); 
     str = str.substring(str1.length()+1, str.length()); 
     str2 = str.substring(0, str.indexOf(";")); 
     str = str.substring(str2.length()+1, str.length()); 
     str3 = str.substring(0, str.indexOf(";")); 
     str4 = str.substring(str3.length()+1, str.length()); 
    } 
    @Override 
    public void onDestroy() { 
     super.onDestroy(); 
     if (handler != null) 
      handler.removeCallbacks(updateTimeTask); 
     handler = null; 
    } 
    private Handler handler = new Handler(); 
} 

回答

2

当你在这里使用HandlerpostDelayed功能是发生了什么:

  1. 处理程序使您Runnable到当前线程的活套队列。
  2. 当时间到了,您的Runnable中的代码在UI线程上运行

请注意,它不是Handler总是将Runnable放到UI线程队列。它将Runnable置为当前线程的队列,并且您当前的线程是UI线程。

所以,如果你把Thread.sleep或其他任何耗费时间的东西(比如网络通信)updateTimeTask它会挂起整个UI线程。

在你的情况下,你应该使用ScheduledExecutorService,见scheduleWithFixedDelay函数。或者作为替代方案,您可以从updateTimeTask功能开始AsyncTask并完成所有重起动功能,并在doInBackgrund功能中执行Thread.sleep

+0

该问题已通过使用handler.postDelayed(

+0

此问题的另一个解决方案是以hh:mm:ss格式匹配时间 – 2011-06-14 07:06:32