我的程序结构如下。我有以下主要活动。此活动将创建“确定位置”对象。此确定位置对象将采用一些参数。其中包括将结果传递给的处理程序。在下面我传入了ThreadHandler,它是MyThreadHandler类型(处理程序的扩展)。这个DetermineLocation对象实现了runnable,在run方法中它查询GPS并将结果传递给threadHandler(传递给DetLoc对象)。 threadHandler实例在创建时接受textview对象(这是要更新的文本视图)
出于调试目的,我已经禁用了GPS更新功能,只有DetLoc的run方法传递一个随机数。然而,这仍然是我的程序崩溃。
崩溃主要发生在将大量输入推送到设备时(例如在多个地方非常快地按下屏幕)。这肯定是一个线程问题,但我不明白为什么。
MAIN:
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.main);
threadModifiedText = (TextView) findViewById(R.id.thread_modified_text);
threadHandler = new MyHandler(threadModifiedText);
//Start up the DetermineLocation thread. This thread will query the GPS every N milliseconds.
// then push the results over hte network if at all possible
DetermineLocation detLoc = new DetermineLocation(this, threadHandler, 3000);
Thread detLocThread = new Thread(detLoc);
detLocThread.start();
}
也是主要的:
class MyHandler extends Handler{
private TextView threadModifiedText;
public MyHandler(TextView tv) {
threadModifiedText = tv;
}
public void handleMessage(Message msg) {
// whenever the Thread notifies this handler we have
// only this behavior
threadModifiedText.setText((CharSequence)msg.obj);
}
}
确定位置类(因为你可以看到GPS的东西已经被注释掉了,它仍然会崩溃):
public class DetermineLocation implements Runnable {
private int updateInterval;
private int provider=3;
private Handler threadHandler;
private Context c;
public final int GPS_ONLY=1;
public final int NETWORK_ONLY=2;
public final int ANY_AVAILABLE=3;
public DetermineLocation(Context c, Handler h, int ui) {
this.c = c;
this.updateInterval = ui;
this.threadHandler = h;
}
public void changeProvider(int providerConst) {
if(providerConst <=3 && providerConst >= 1)
provider = providerConst;
}
public void changeUpdateInterval(int updateIntervalMS) {
if(updateIntervalMS >= 0)
this.updateInterval = updateIntervalMS;
}
@Override
public void run() {
Message m = new Message();
//LocationManager locationManager = (LocationManager)c.getSystemService(Context.LOCATION_SERVICE);
//Location loc = locationManager.getLastKnownLocation(LocationManager.NETWORK_PROVIDER);
while(true) {
CharSequence cs = Math.random() + "\r\n"; //+ loc.getLatitude() + " " + loc.getLongitude();
m.obj = cs;
threadHandler.sendMessage(m);
try {
Thread.sleep(updateInterval);
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
}
答案 0 :(得分:3)
您似乎只是实例化Message
,在后台线程上连续编写,然后从UI线程连续读取,没有同步。事情发展并不奇怪。
您可以通过对线程边界发送的每条消息使用Message.obtain()
来解决此问题,也可以使用AsyncTask
使您的生活变得更加简单。
使用AsyncTask
,您不需要任何Handlers
或Runnables
...它会使线程变得如此简单。