内存优化

1、Java的四种引用,强弱软虚,及其适用的场景。

- 强引用:
   - 强引用可以直接访问目标对象。
   - 强引用所指向的对象在任何时候都不会被系统回收。JVM宁愿抛出OOM异常,也不会回收强引用所指向的对象。
   - 强引用可能导致内存泄露。

- 软引用:
  - 在OutOfMemory异常发生之前,被占用的内存空间可以被释放掉的,从而避免内存达到上限,避免Crash发生。
  - 需要注意的是,在垃圾回收器对这个Java对象回收前,SoftReference类所提供的get方法会返回Java对象的强引用,一旦垃圾线程回收该Java对象之后,get方法将返回null。所以在获取软引用对象的代码中,一定要判断是否为null,以免出现NullPointerException异常导致应用崩溃。     
  
  - 如果只是想避免OutOfMemory异常的发生,则可以使用软引用。如果对于应用的性能更在意,想尽快回收一些占用内存比较大的对象,则可以使用弱引用。
  - 还有就是可以根据对象是否经常使用来判断。如果该对象可能会经常使用的,就尽量用软引用。如果该对象不被使用的可能性更大些,就可以用弱引用。

- 弱引用:在系统GC时,只要发现弱引用,不管系统堆空间是否足够,都会将对象进行回收。但是,由于垃圾回收器的线程通常优先级很低,因此,并一不定能很快的发现持有弱引用的对象。这种情况下,弱引用对象可以存在较长的一段时间。一旦一个弱引用对象被垃圾回收器回收,便会加入到一个注册引用队列中。 

  实际应用:播放器的播放Panel,是一个View,就是在视频播放时,可以show、hide, 也可以拖拽进度条之类,还有上面的音量,亮度调节等。这样一个view,我们用弱引用,因为在视频播放过程中,不论硬解还是软解,都将占用大量内存。

-  虚引用:
   - 虚引用是所有引用类型中最弱的一个。一个持有虚引用的对象,和没有引用几乎是一样的,随时都可能被垃圾回收器回收。当试图通过虚引用的get()方法取得强引用时,总是会失败。并且,虚引用必须和引用队列一起使用,它的作用在于跟踪垃圾回收过程。
   - 当垃圾回收器准备回收一个对象时,如果发现它还有虚引用,就会在垃圾回收后,销毁这个对象,奖这个虚引用加入引用队列。

2、内存泄漏如何产生,常见的Android内存泄漏的场景,怎么解决。

- 单例造成的内存泄露。
- 匿名内部类/非静态内部类和异步线程。
 

  public class MainActivity extends AppCompatActivity {

        private static TestResource mResource = null;

        @Override
        protected void onCreate(Bundle savedInstanceState) {
            super.onCreate(savedInstanceState);
            setContentView(R.layout.activity_main);
            if (mManager == null) {
                mManager = new TestResource();
            }
        }

       class TestResource {
            
        }
    }

   每次启动Activity时都会使用该单例的数据,这样虽然避免了资源的重复创建,不过这种写法却会造成内存泄漏,因为非静态内部类默认会持有外部类的引用,而该非静态内部类又创建了一个静态的实例,该实例的生命周期和应用的一样长,这就导致了该静态实例一直会持有该Activity的引用,导致Activity的内存资源不能正常回收。

   正确的做法为:将该内部类设为静态内部类或将该内部类抽取出来封装成一个单例。

- 匿名内部类:android开发经常会继承实现Activity/Fragment/View,此时如果你使用了匿名类,并被异步线程持有了,那要小心了,如果没有任何措施这样一定会导致泄露。
- Handler 造成的内存泄漏。
- 集合类泄漏。

3、怎么发现和分析内存泄漏。

发现内存泄漏:

一、内存泄漏的检查方法:
    1.ccmalloc-Linux和Solaris下对C和C++程序的简单的使用内存泄漏和malloc调试库。
    2.Dmalloc-Debug Malloc Library.
    3.Electric Fence-Linux分发版中由Bruce Perens编写的malloc()调试库。
    4.Leaky-Linux下检测内存泄漏的程序。
    5.LeakTracer-Linux、Solaris和HP-UX下跟踪和分析C++程序中的内存泄漏。
    6.MEMWATCH-由Johan Lindh编写,是一个开放源代码C语言内存错误检测工具,主要是通过gcc的precessor来进行。
    7.Valgrind-Debugging and profiling Linux programs, aiming at programs written in C and C++.
    8.KCachegrind-A visualization tool for the profiling data generated by Cachegrind and Calltree.
    9.IBM Rational PurifyPlus-帮助开发人员查明C/C++、托管.NET、Java和VB6代码中的性能和可靠性错误。PurifyPlus 将内存错误和泄漏检测、应用程序性能描述、代码覆盖分析等功能组合在一个单一、完整的

你可能感兴趣的:(Android技术点,内存泄漏,内存优化,JAVA引用)