zoukankan      html  css  js  c++  java
  • [Java] 一、对象的创建 & 销毁

    *1、考虑静态工厂方法(static factory method)代替构造器?!优势?不足?

    服务提供者架构:

    1、服务接口(Service Interface) -- 提供者实现的;

    2、提供者注册API(Provider Registration API)--系统用于注册实现,让客户端访问它们;

    3、服务访问API(Service Access API)--客户端用于获取服务的实例;[它是“灵活的静态工厂”,构成了服务提供者架构的基础!]

           *4、服务提供者接口(Service Provider Interface)--这些提供者负责创建其服务实现的实例

         [如果没有Service Provider Interface,实现就按照类名称注册,并通过反射方式进行实例化。

    对于JDBC来说,

    Connection就是它的服务接口,

    DriverManager.registerDriver是提供注册API,

    DriverManager.get Connection是服务访问API,

    Driver就是服务提供者接口]

    2、遇到多个构造器参数时要考虑用构造器

    *3、用私有构造器or枚举类型强化Singleton属性

    4、通过私有构造器强化不可实例化的能力

    5、避免创建不必要的对象

    *6、消除过期的对象引用

    // Can you spot the "memory leak"?
    public class stack {
        private Object[] elements;
        private int size = 0;
        private static final int DEFAULT_INITIAL_CAPACITY = 16;
    
        public Stack() {
            elements = new Object[DEFAULT_INITIAL_CAPACITY];
        }
        
        public void push(Object e) {
            ensureCapacity();
            elements[size++] = e;
        }
        
        public Object pop() {
            if (size == 0)
                throw new EmptyStackException();
            return elements[--size];
        }
    
        /**
         * Ensure space for at least one more element, roughly
         * doubling the capacity each time the array needs to grow.
         */
        private void ensureCapacity() {
            if (elements.length == size)
                elements = Arrays.copyOf(elements, 2*size+1);
        }
    }

    BUG:“内存泄漏”,随着垃圾回收器活动的增加,或者由于内存占用的不断增加,程序性能的降低逐渐表现出来。极端情况、

    会导致磁盘交换(Disk Paging),甚至导致程序报错(OutOfMemoryError)--少见!

    eg:如果一个栈先是增长,再收缩,那么从栈中弹出来的对象将不会被当作垃圾回收,即使使用栈的程序不再引用这些对象,它们也

    不会被回收。因为:栈内部维护着对这些对象的过期引用(obsolete reference)--即永远也不会再被解除的引用。本例中,elements

    数组的“活动部分(active portion)”之外的任何引用都是过期的。活动部分指:elements中下标小于size的那些元素。

    fix bug:一旦对象引用过期,需要清空这些引用。即修改pop方法,如下;

        public Object pop() {
            if (size == 0)
                throw new EmptyStackException();
            Object result = elements[--size];
            elements[size] = null; // Eliminate obsolete reference.
            return result;
        }

    好处:

    1、解决BUG出现的内存长期占用,降低性能;

    2、如果它们以后又被错误的解除引用,程序就会抛出NullPointerException异常,而不是悄悄继续运行下去!

    /**

        * 1、只要是自己管理内存,程序员就应该警惕内存泄露问题;

        *

        * 2、缓存;--把对象引用放到缓存中,它就很容易被遗忘掉;

    [修复:只要在缓存之外存在某个项的键的引用,该项就有意义,那么就可以用WeakHashMap代表缓存!

      “缓存项的生命周期是否有意义”--不容易确定。LinkedHashMap类利用它的removeEldestEntry方法!

      更加复杂的缓存,必需直接使用java.lang.ref!]

        *

        * 3、监听器 & 其他回调

    [eg:如果你实现一个API,客户端在这个API中注册回调,却没有显式地取消注册,那么除非你采取某些动作,否则

      它们就会聚集。确保回调立即被当作垃圾回收的最佳方法是只保存它们的弱引用(weak reference),例如,只将它们

    保存成WeakHashMap中的键。]

        *

        **/

    7、避免使用终结方法?(即finalizer)

    “不要把终结方法当作是C++析构器的对应物!(构造器)”

    C++:析构器(destructors)回收一个对象所占用的资源,是构造器所必需的对应物; --也可以回收其他的非内存资源

    Java:当一个对象变得不可到达时,垃圾回收机制会回收与该对象相关联的存储空间;--用try-finally实现类似工作

    ........................................................................

    Effective Java 

      -- Second Edition (James Gosling)

    ........................................................................

  • 相关阅读:
    WebGIS前端地图显示之根据地理范围换算出瓦片行列号的原理(核心) 【系列1-1】
    WMTS服务
    WebGIS 分辨率 比例尺和切片
    Mysql Spatial 空间查询参考
    webapi和传统mvc的context和request的区别
    IIS启动32位运行库
    GEOJSON标准格式学习
    gdal笔记之获取矢量面边界点坐标
    关于TensorFlow,你应该了解的9件事
    C#根据时间范围获取每年每月每周的分组
  • 原文地址:https://www.cnblogs.com/Trybst/p/5498474.html
Copyright © 2011-2022 走看看