Java 处理器内存泄漏?
我有一个在主线程上声明的处理程序:Java 处理器内存泄漏?,java,android,memory-leaks,Java,Android,Memory Leaks,我有一个在主线程上声明的处理程序: mainHandler = new Handler() { @Override public void handleMessage(Message msg) { switch (msg.what) { case 1: Bundle bundle = msg.getData();
mainHandler = new Handler() {
@Override
public void handleMessage(Message msg) {
switch (msg.what) {
case 1:
Bundle bundle = msg.getData();
mTextView.setText(bundle.getString("message"));
break;
. . .
default:
super.handleMessage(msg);
break;
}
}
};
其中mTextView是在create()上定义的文本视图
我有一个单独线程中使用的任务。runnable从主线程存储mainHandler
,并告诉它发送消息:
public class SomeRunnable implements Runnable {
private Handler mHandler;
public SomeRunnable(Handler handler) throws IOException {
. . .
mHandler = handler;
}
@Override
public void run() {
while (!Thread.currentThread().isInterrupted()) {
try {
. . .
Message msg = mHandler.obtainMessage();
. . .
mHandler.sendMessage(msg);
}
} catch (IOException e) {
Log.e("Error", e.hashCode() + ": " + e.getLocalizedMessage());
}
}
}
我已经看到,如果处理程序类不是静态的,那么使用Handler#postDelayed()
等方法可能会造成内存泄漏。但是,我使用的是处理程序#sendMessage()
,它可以立即将消息放入消息队列
我仍然有内存泄漏的危险吗?即使:
@Override
protected void onDestroy() {
super.onDestroy();
mThread.interrupt();
mainHandler.removeCallbacksAndMessages(null);
}
谢谢大家! 为了解决所有可能发生的情况,您可以将
mHandler
aWeakReference
设置为如下所示:
public class SomeRunnable implements Runnable {
private WeakReference<Handler> mHandlerRef;
public SomeRunnable(Handler handler) throws IOException {
. . .
mHandlerRef = new WeakReference<Handler>( handler );
}
@Override
public void run() {
while (!Thread.currentThread().isInterrupted()) {
try {
. . .
Handler mHandler = mHandlerRef.get();
if( mHandler != null ) {
Message msg = mHandler.obtainMessage();
. . .
mHandler.sendMessage(msg);
}
}
} catch (IOException e) {
Log.e("Error", e.hashCode() + ": " + e.getLocalizedMessage());
}
}
}
}
public类SomeRunnable实现Runnable{
私人WeakReference mHandlerRef;
公共SomeRunnable(处理程序)引发IOException{
. . .
mHandlerRef=新的WeakReference(处理程序);
}
@凌驾
公开募捐{
而(!Thread.currentThread().isInterrupted()){
试一试{
. . .
Handler mHandler=mHandlerRef.get();
if(mHandler!=null){
Message msg=mHandler.obtainMessage();
. . .
mHandler.sendMessage(msg);
}
}
}捕获(IOE异常){
Log.e(“Error”,e.hashCode()+”:“+e.getLocalizedMessage());
}
}
}
}
您发布的代码不清楚,但是您的处理程序
或可运行
是否包含对非瞬态对象的引用?此外,与您似乎所说的相反,我希望静态ly-hold处理程序比我上面看到的更容易发生内存泄漏。@323go我的可运行“SomeRunnable”与主线程中的处理程序“mainHandler”具有相同的地址。这就是你所定义的非暂时性吗?我的处理程序不包含任何引用,尽管它引用了主线程中的TextView。为了安全起见,您可以引用mainHandler
aWeakReference
。扎克,另一种方法是,如果您使用的是Eclipse
,则使用Eclipse内存分析器。查看应用程序是否泄漏内存,使用该工具还可以确定导致程序泄漏的原因。看@Mike我今天早上刚下载了这个。谢谢你的建议。我一定会尝试一下,分析一下记忆。我只是想问一下,从概念上讲,我的实现是否存在潜在的内存泄漏。谢谢你的建议!我将看看这对我的应用程序有何影响,我会让您知道我的最终解决方案;每次在while循环内调用,还是可以在循环外执行?这取决于您在循环中做了多少工作,或者您是否让位于循环中的其他线程。运行
将在发布后很快执行;使用WeakReference
唯一有帮助的情况是,如果您有一个长时间运行的Runnable
,您希望它能够干净地中断/中止。Runnable在一个单独的线程中执行,并一直持续到应用程序终止。然后您一定要调用get()
在使用它之前,引用的处理程序可能已经不存在了。如果它返回null
,这也是停止线程执行的信号。