简体   繁体   English

如何在Android中使用多线程处理事件处理功能(SensorListeners)

[英]How to use MultiThreading in Android for an Event Handling Function (SensorListeners)

I have an event handling mechanism in my Android code to dump the sensor values in a file. 我的Android代码中有一个事件处理机制,可将传感器值转储到文件中。 Right now, I'm doing it in the main UI thread and hence the UI button responsiveness is very sluggish and I would like to speed it up. 现在,我正在主UI线程中执行此操作,因此UI按钮的响应速度非常缓慢,因此我想加快速度。

How can I use multithreading on event handling functions? 如何在事件处理功能上使用多线程? I'm trying to do it like this: 我正在尝试这样做:

  1. Create a global variable writeNow. 创建一个全局变量writeNow。
  2. When the sensor value changes, set WriteNow = true 传感器值更改时,将WriteNow设置为true
  3. Create a thread in the class which looks like this: 在类中创建一个如下所示的线程:

     Thread thread1 = new Thread() { public void run() { if(writeNow == true) { try { fos.write(s.getBytes()); } catch (IOException e) { e.printStackTrace(); } writeNow = false; } } }; 

Thus, whenever writeNow is true, it will write to a File and then set WriteNow to false. 因此,只要writeNow为true,它将写入文件,然后将WriteNow设置为false。 However, I realize this is not the right approach, because the thread will execute once and then stop executing. 但是,我意识到这不是正确的方法,因为线程将执行一次,然后停止执行。 When I tried a simple example with a while(true) and wait(), I found that the thread is interrupted millions of times. 当我尝试使用while(true)和wait()的简单示例时,我发现该线程被中断了数百万次。

So how do I enclose this event handling mechanism in a single thread, for speeding up a process? 那么,如何将这种事件处理机制封装在单个线程中,以加快处理速度?

Thanks! 谢谢!

You can try one of the following approaches: 您可以尝试以下方法之一:

  1. It looks like you're trying to keep your writer thread running all the time; 看来您正在尝试使编写器线程始终保持运行状态; what you can do is spawn the thread only when you need it. 您只能在需要时才生成线程。 Take a look at the example in the Android documentation for handling expensive operation in the UI thread . 看一下Android文档中用于处理UI线程中昂贵操作的示例。

    Here is the example from that page: 这是该页面上的示例:

     public class MyActivity extends Activity { [ . . . ] // Need handler for callbacks to the UI thread final Handler mHandler = new Handler(); // Create runnable for posting final Runnable mUpdateResults = new Runnable() { public void run() { updateResultsInUi(); } }; @Override protected void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); [ . . . ] } protected void startLongRunningOperation() { // Fire off a thread to do some work that we shouldn't do directly in the UI thread Thread t = new Thread() { public void run() { mResults = doSomethingExpensive(); mHandler.post(mUpdateResults); } }; t.start(); } private void updateResultsInUi() { // Back in the UI thread -- update our UI elements based on the data in mResults [ . . . ] } } 

    Since it doesn't look like you're doing anything in the UI thread once you finish writing you don't really need to bother with a Handler . 由于看起来不像在完成编写后就在UI线程中执行任何操作,因此您实际上无需费心Handler But you might want to use it to display a Toast once the file has been written to. 但是,一旦文件被写入,您可能希望使用它来显示Toast

  2. On the other hand, if you still want to have a thread running, you might have it sleep() and periodically wake up and check the status of writeNow . 另一方面,如果仍然要运行线程,则可以使其处于sleep()并定期唤醒并检查writeNow的状态。

     Thread thread1 = new Thread() { public void run() { while(true) { if(writeNow == true) { try { fos.write(s.getBytes()); } catch (IOException e) { e.printStackTrace(); } writeNow = false; } try { Thread.sleep(100); //sleep for 100 ms } catch (InterruptedException e) { Log.d('', e.getMessage()); } } } }; 

    Note that this will quickly get complicated and you might lose the bytes you want to write if your thread is sleeping when new data comes in and when it wakes up, even newer data has been received and has overwritten the previous bytes. 请注意,这很快就会变得很复杂,如果线程在新数据传入或唤醒时处于休眠状态,则即使您收到新数据并覆盖了先前的字节,如果线程正在休眠,您可能会丢失想要写入的字节。 You'd need some sort of a queue to manage that. 您需要某种队列来进行管理。

  3. I'm not sure what you were doing with the wait() but that should've also worked and is in fact, the approach for problems involving a consumer and producer. 我不确定您在使用wait()做什么,但是那也应该起作用,并且实际上是解决涉及消费者和生产者的问题的方法。 The idea is to have your thread synchronize and wait() on a shared object (like perhaps your queue of bytes); 想法是让您的线程在共享对象上同步并wait() (例如您的字节队列); a second thread will call notify() on the shared object when there is data available to write and the writer thread will be woken up. 当有可用数据写入时,第二个线程将在共享库上调用notify() ,并唤醒写程序线程。 The writer thread should then write and reloop. 然后,写程序线程应写并重新循环。 Take a look at this tutorial . 看一下本教程

    As for the interruption of your thread, your thread may be interrupted for a number of reasons which is why it is good practice (especially when using wait() ) to ensure that the condition you checked before you called wait() is still valid because you could've been woken because of either a call to notify()/notifyAll() or because of an interruption. 至于线程的中断,您的线程可能由于多种原因而被中断,这就是为什么最好的做法(尤其是在使用wait() ),以确保调用wait() 之前检查的条件仍然有效,因为您可能是因为调用notify()/notifyAll()或由于中断而被唤醒。

Handler handler = null;

handler = new Handler();

//create another class for and make consrtuctor as u want. so that u can use that effectively.
//for example.                                                      

popupIndex = new IndexThread(handler,head, target,ltp,price,IndexNifty.this,columsView,call);           

popupIndex.setColumnViewexit(columsView);
handler.postDelayed(popupIndex, 300);


//another class
public IntraThread(Handler handler,String script,int target,int ltp,int price,Intraday intraday,TextView columsView,String call){
        super();
        this.target = target;
        this.ltp = ltp;
        this.price = price;     
        this.intraday = intraday;
        this.columsView = columsView;
        this.script= script;
        this.handler= handler;
        this.call= call;
}

public void run(){
// write ur code here....
}

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM