1.mContext---

public class LoginActivity extends BaseActivity {
....
     /**初始化信息*/
     private void init() {
          DatabaseHelper.getInstance(this, GlobalVar.DB_NAME);//初始化数据库,复制数据库文件
          // 初始化屏幕数据
          Configuration.initDisplayMetrics(getWindowManager());
          SystemSettingHelper.initContext(this);    
          ...
          }
     .....
     }

----------------------------------------------------------------------------------------------------    
     public class DatabaseHelper extends SQLiteOpenHelper {
    
     private Context mContext;
     .....
     private DatabaseHelper(Context context, String name) { 
          super(context, name, null, VERSION);
          mContext = context;
          ..
          }
          ....
          public static final DatabaseHelper getInstance(Context context, String name){
          initDatabaseNames(context);
          copyDatabaseFile(context,name);
          return new DatabaseHelper(context,name); 
     }
     ....
     }
----------------------------------------------------------

public class SystemSettingHelper {
private static Context mContext = null;
    
     public static final void initContext(Context context){
          mContext = context;
     }
     .....
    
}

 
 
今天,看到一段,内存泄漏的代码。
 
static类型的变量,是类的类型信息。
一个虚拟机实例,当访问一个类的静态方法,或者实例化一个类的时候,虚拟机会首先加载类的类型数据(class data)。
类型数据,存放在方法区中。
 
一定出现内存泄漏的代码:
下述代码,传递指向LoginActivity对象的引用给SystemSettingHelper的静态方法initContext,
并且引用值,是作为SystemSettingHelper的静态变量存在的。
那么,根据GC_ROOT垃圾回收算法,mContext可以作为GC_ROOT,从GC_ROOT到LoginActivity对象存在一个可达路径。所以,LoginActivity对象是不会被回收的。
 
只有,当java虚拟机卸载类SystemSettingHelper时,才释放了对LoginActivity的引用。
 
登陆界面,一登陆完毕了;然后,就跳转到其他页面去了;然后,在资源不足的时候,系统就会回收不是处于onResume状态的Activity,比如LoginActivity。如此,系统调用了LoginActivity的onDestroy,但是,却垃圾收集却没有回收LoginActivity对象。如此,就不知道如何引用LoginActivity。
 
它存在,但是,我却找不到可以引用它的变量,也就是泄漏了。
 
public class LoginActivity extends BaseActivity {
....
     /**初始化信息*/
     private void init() {
          DatabaseHelper.getInstance(this, GlobalVar.DB_NAME);//初始化数据库,复制数据库文件
          // 初始化屏幕数据
          Configuration.initDisplayMetrics(getWindowManager());
          SystemSettingHelper.initContext(this);    
          ...
          }
     .....
     }
 
public class SystemSettingHelper {
private static Context mContext = null;
    
     public static final void initContext(Context context){
          mContext = context;
     }
     .....
    
}
 
 
---------------------------------------------------
 
同样的分析,如果 public static final DatabaseHelper getInstance(Context context, String name)
返回值,作为某个类的静态变量的值,那么,同样是会出现内存泄漏。
 
     public class DatabaseHelper extends SQLiteOpenHelper {
    
     private Context mContext;
     .....
     private DatabaseHelper(Context context, String name) { 
          super(context, name, null, VERSION);
          mContext = context;
          ..
          }
          ....
          public static final DatabaseHelper getInstance(Context context, String name){
          initDatabaseNames(context);
          copyDatabaseFile(context,name);
          return new DatabaseHelper(context,name); 
     }
     ....
     }
 
 
解决办法:
将上述的context,换位ApplicationContext。一个应用,有一个ApplicationContext,它指向的是应用的Application对象。
这个对象会一直存在着,直到应用销毁。
 
如此,就可以避免发生LoginActivity对象泄漏的情况。
 
 
---------------------Java虚拟机卸载已经加载到方法区的类的时机----------------------------------
 
引用自:http://blog.csdn.net/zhengzhb/article/details/7331354
  • 该类所有的实例都已经被回收,也就是java堆中不存在该类的任何实例。
  • 加载该类的ClassLoader已经被回收。
  • 该类对应的java.lang.Class对象没有任何地方被引用,无法在任何地方通过反射访问该类的方法。

static变量与context泄漏的更多相关文章

  1. 局部变量存储区域静态变量存储区域static变量存储区域

    局部变量存储区域静态变量存储区域static变量存储区域 常见的存储区域可分为: 1.栈 由编译器在需要的时候分配,在不需要的时候自动清楚的变量的存储区.里面的变量通常是局部变量.函数参数等. 2.堆 ...

  2. Android开发中使用static变量应该注意的问题

    package com.highxin.launcher01; import java.util.ArrayList; import java.util.HashMap; import java.ut ...

  3. Android开发 静态static类与static方法持有Context是否导致内存泄露的疑问

    简述 在Android开发的过程中,难免会使用单例模式或者静态方法工具类.我们会让它们持有一些外部的Context或者View一般有以下几种情况: 单例模式,类的全局变量持有Context 或 Vie ...

  4. java中static变量和方法的总结

    转自:http://blog.csdn.net/haobo920/article/details/5921621 java中static变量和方法的总结 java中一切皆是对象 一个类中对象的定义一般 ...

  5. Asp.net中static变量和viewstate的使用方法(谨慎)

    在.Net平台下进行CS软件开发时,我们经常遇到以后还要用到某些变量上次修改后的值,为了简单起见,很多人都习惯用static来定义这些变量,我也是.这样非常方便,下一次调用某个函数时该变量仍然保存的是 ...

  6. ecmall中static变量的使用-model模型代码设计

    function &m($model_name, $params = array(), $is_new = false) { static $models = array(); $model_ ...

  7. objective-c static变量的使用总结

    在java中,我们经常使用的是单例模式,这些设计模式在ios开发中也比较常用,最近也在考虑使用在ios开发中使用单例模式 在objective-c中,需要在.m文件里面定义个static变量来表示全局 ...

  8. 调整static变量初始化顺序的一个办法

    // wrap the LaunchDir variable in a function to work around static/global initialization order stati ...

  9. spring为什么不能注入static变量

    Spring 依赖注入 是依赖 set方法 set方法是 是普通的对象方法 static变量是类的属性 @Autowired private static JdbcTemplate jdbcTempl ...

随机推荐

  1. Unity3D 入门 - 工作区域介绍 与 入门示例

    一. 工作区域详解 1. Scence视图 (场景设计面板) scence视图简介 : 展示创建的游戏对象, 可以对所有的游戏对象进行 移动, 操作 和 放置; -- 示例 : 创建一个球体, 控制摄 ...

  2. 第一次课堂作业---circle

    链接:circle

  3. LintCode-70.二叉树的层次遍历 II

    二叉树的层次遍历 II 给出一棵二叉树,返回其节点值从底向上的层次序遍历(按从叶节点所在层到根节点所在的层遍历,然后逐层从左往右遍历) 样例 给出一棵二叉树 {3,9,20,#,#,15,7}, 按照 ...

  4. python-网易云简单爬虫

    一.准备工作 1.使用python3.6和pycharm 2.使用的模块 tkinter .requests .beautifulSoup.getpass.os 3.网易云的榜单页面地址 https: ...

  5. matlab中的静态变量

    persistent X Y Z 将X,Y,Z定义为在其声明处的函数的局部变量.然而,这些变量的值在函数调用期间在内存中保存(应该是堆区).Persistent 变量和global(全局)变量相似,因 ...

  6. Redis架构演变与redis-cluster群集读写方案

    导言 redis-cluster是近年来redis架构不断改进中的相对较好的redis高可用方案.本文涉及到近年来redis多实例架构的演变过程,包括普通主从架构(Master.slave可进行写读分 ...

  7. 只要访问的地址匹配cookie的地址时候 发送request请求时候 会携带上该cookie

    只要访问的地址匹配cookie的地址时候 发送request请求时候 会携带上该cookie

  8. BZOJ2049:[SDOI2008]洞穴勘测——题解

    http://www.lydsy.com/JudgeOnline/problem.php?id=2049 https://www.luogu.org/problemnew/show/P2147 辉辉热 ...

  9. iOS图片上传后被旋转的问题

    最近用PHP做了一个图片合成程序,前端是通过HTML的file input选取自定图片,POST到php后台调整尺寸后与事先准备好的背景图进行合成. 通过测试发现,上传后的自定图片有的被旋转了,有的是 ...

  10. 51nod 1296 有限制的排列(DP)

    对于一个i,如果要比邻居大,那么i比i-1大,i+1比i小,比邻居小同理.设v[i]=0表示i与i-1的关系无限制,v[i]=1表示a[i-1]>a[i],v[i]=2表示a[i-1]<a ...