之前一直搞不懂内存泄漏和内存溢出,现在有时间了,仔细研究了一下。
首先:内存泄漏:给一个对象申请一块内存空间,由于某种原因这块内存未释放掉,这块内存被占用导致应用卡顿等。
内存溢出:拥有一块20字节的内存空间,你将30字节的文件写入其中,就会造成溢出。
由于内存泄漏,最终会导致内存溢出(OOM),导致系统崩溃。
内存溢出的几种情况:
1.静态activity
如果activity实例被静态变量引用,在activity被销毁的时候,若activity实例未被释放,就会造成内存泄漏。
(在activity的onDestory()时,应将该对象释放掉)
2.静态View
①单例设计模式应尽量不要使用。(干预activity生命周期的操作,避免这么做)
②当一个view对象attach到activity中时,view内部就持有了一个指向activity的引用。(不要把一个attach到activity上的view设置为静态的。)
3.内部类
若封装一个内部类,并通过静态变量拥有了它。(内部类可直接访问他的外部类的变量,也就是内部类隐式的持有一个对他的外部类的一用,间接导致了泄漏activity。)
4.匿名类
匿名类也持有一个指向声明的它的类的引用。
5.handler
匿名Runnable类,将其加入handler处理队列。在activity被销毁的时候,若这个消息还没有被处理,就有一个指向activity的引用未被释放。
6.线程
7.定时任务
线程、定时任务若通过匿名内部类的方式实例的,即使工作在另一条线程,依旧存在一个指向activity的引用,导致内存泄漏。
8.系统服务
通过Context的getSystemService()得到服务。
注册服务时(系统服务会持有一个对activity对象的引用),若activity销毁时忘记取消注册监听,就会发生泄漏。
记得给一个控件ImageView 添加一张图片,就出现了内存溢出的错误提示。后来对图片进行处理之后才使用。在项目的过程中,可能会使用全局静态变量等类似的请况,不要忘记对它做处理。否则很可能发生内存泄漏,进而导致内存溢出。