android 内存泄漏处理方式

由于某个对象持有了其他对象的引用导致 ,导致无法 GC。

1:合理的使用context–比如我们常使用的Toast,Service,最好使用getApplicationContext(),因为这些在activity结束的时候可能仍在运行
下图通过图片说明国关于context的使用)

2:不要在activity中使用AsyncTask的强引用,如下是不行的:

class MyActivity extends Activity {
  private AsyncTask<Void, Void, Void> myTask = new AsyncTask<Void, Void, Void>() {
    //内部类隐含了对activity的一个强引用,强引用是无法被gc回收的;
  }
}

我们异步获取手机音频文件 做个小范例:

 private static class ScanRingsPhoneMusic extends AsyncTask<Void, Void, Void > {
        private WeakReference<MusicListActivity> activityReference;
        // only retain a weak reference to the activity
        ScanRingsPhoneMusic(MusicListActivity context) {
            activityReference = new WeakReference<>(context);

        }
        @Override
        protected Void doInBackground(Void... voids) {
            MusicListActivity activity = activityReference.get();
            getAllSongs(activity);
            return null;
        }
    }

    @Override
    protected void onDestroy() {
        super.onDestroy();
        PublicUtils.getInstance().mediaPlayerRelease();
        mHandler.removeCallbacksAndMessages(null);
    }


    public static void  getAllSongs(MusicListActivity activity) {
        Cursor cursor = activity.getApplicationContext().getContentResolver().query(
                MediaStore.Audio.Media.EXTERNAL_CONTENT_URI,
                new String[] { MediaStore.Audio.Media._ID,
                        MediaStore.Audio.Media.DISPLAY_NAME,
                        MediaStore.Audio.Media.TITLE,
                        MediaStore.Audio.Media.DURATION,
                        MediaStore.Audio.Media.ARTIST,
                        MediaStore.Audio.Media.ALBUM,
                        MediaStore.Audio.Media.YEAR,
                        MediaStore.Audio.Media.MIME_TYPE,
                        MediaStore.Audio.Media.SIZE,
                        MediaStore.Audio.Media.DATA },
                MediaStore.Audio.Media.MIME_TYPE + "=? or "
                        + MediaStore.Audio.Media.MIME_TYPE + "=?",
                new String[] { "audio/mpeg", "audio/x-ms-wma" }, null);
        if (cursor.moveToFirst()) {

            BackGroundMusic backGroundMusic = null;

            while (cursor.moveToNext()) {
                backGroundMusic = new BackGroundMusic();
                // 文件名
                backGroundMusic.setFileName(cursor.getString(1));
                // 歌曲名
                backGroundMusic.setTitle(cursor.getString(2));
                // 时长
                backGroundMusic.setDuration(cursor.getInt(3));
                // 歌手名
                backGroundMusic.setSinger(cursor.getString(4));
                // 专辑名
                backGroundMusic.setAlbum(cursor.getString(5));
                // 年代
                if (cursor.getString(6) != null) {
                    backGroundMusic.setYear(cursor.getString(6));
                } else {
                    backGroundMusic.setYear("未知");
                }
                // 歌曲格式
                if ("audio/mpeg".equals(cursor.getString(7).trim())) {
                    backGroundMusic.setType("mp3");
                } else if ("audio/x-ms-wma".equals(cursor.getString(7).trim())) {
                    backGroundMusic.setType("wma");
                }
                // 文件大小
                if (cursor.getString(8) != null) {
                    float size = cursor.getInt(8) / 1024f / 1024f;
                    backGroundMusic.setSize((size + "").substring(0, 4) + "M");
                } else {
                    backGroundMusic.setSize("未知");
                }
                // 文件路径
                if (cursor.getString(9) != null) {
                    backGroundMusic.setFilePath(cursor.getString(9));
                }
                    Message message = activity.mHandler.obtainMessage();
                    message.what = 1;
                    message.obj=backGroundMusic;
                    activity.mHandler.sendMessage(message);
                Log.i(TAG, backGroundMusic.toString());
            }
            cursor.close();
        }
        return ;
    }

 最后 附加一个 防止handler 内存泄漏的code

 /**
     * weakReference 防止内存泄漏
     */
    private static class MyHandler extends Handler {
        private WeakReference<MusicListActivity> weakReference;
         MyHandler(MusicListActivity activity) {
            weakReference = new WeakReference<>(activity);
        }
        @Override
        public void handleMessage(Message msg) {
            super.handleMessage(msg);
            Log.e(TAG, "handleMessage: ");
            MusicListActivity activity = weakReference.get();
            switch (msg.what) {
                case 1:
                    if (activity != null) {
                        BackGroundMusic backGroundMusic= (BackGroundMusic) msg.obj;

                        activity.mBackGroundMusicList.add( backGroundMusic);
                        if(activity.mBackGroundMusicList.size()>0){
                            activity.musicAdapter.notifyDataSetChanged();
                        }
                    }
                    break;
                case 2:
                    activity.musicAdapter.notifyDataSetChanged();
                    break;
            }
        }
    }

关于Android的内存泄漏 小伙伴 学会了吗?

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值