LruCache和TreeMap实现 数组池 复用 android

内存抖动—>频繁的创建对象和销毁会导致程序一直gc会导致卡顿,严重可能会导致OOM

当处理 int[] byte[] 数组时,可以创建对象数组池来进行对象的复用(减少对象的创建),降低内存抖动,提高性能。

LruCache

LruCache是一个缓存池,里面封装了LinkHashMap和一个双向链表。可以参考Glide的复用机制。
来进行数组的复用。

// An highlighted block
public class ArrayPool3 implements ArrayPool {

    private static final String TAG = "ArrayPool";

    public static final int ARRAY_POOL_SIZE_BYTES = 4 * 1024 * 1024;
    private int maxSize;

    private LruCache<Integer, byte[]> cache;
    //key 为byte数组长度,value为个数
    private final NavigableMap<Integer, Integer> sortedSizes = new TreeMap<>();

    public ArrayPool3() {
        this(ARRAY_POOL_SIZE_BYTES);
    }

    public ArrayPool3(int maxSize) {
        this.maxSize = maxSize;
        this.cache = new LruCache<Integer, byte[]>(maxSize) {
            protected int sizeOf(Integer key, byte[] value) {
                return value.length;
            }
        };
    }

    @Override
    public synchronized byte[] get(int len) {
        //获得等于或大于比len大的key
        Integer key = sortedSizes.ceilingKey(len);
        if (key != null) {
            byte[] bytes = cache.remove(key);
            //计数器 -1
            Integer current = sortedSizes.get(key);
            if (current == 1) {
                sortedSizes.remove(key);
            } else {
                sortedSizes.put(key, current - 1);
            }
            return bytes;
        }
        return new byte[len];
    }
    @Override
    public synchronized void put(byte[] data) {
        if (data == null || data.length == 0 || data.length > maxSize) return;
        int length = data.length;
        Integer current = sortedSizes.get(length);
        //计数器+1
        sortedSizes.put(length, current == null ? 1 : current + 1);
        cache.put(length, data);
    }


}

通过LruCache<Integer,(数组)>来进行记录 key值记录了数组的长度,value则是数组。

通过remove方法从cache中取值,通过put向cache中添加(数组使用完后调用put方法)

这样可以完成数组的复用,但是每次的length都是固定的,多大的length只能从池子中获取多大的数组(仅适用于数组大小固定)

通过TreeMap来记录所需数组的长度----->实现数组不同长度的复用

TreeMap底层的实现是红黑树,可以将key有序的排列(HashMap不可以)

		    private final NavigableMap<Integer, Integer> sortedSizes = new TreeMap<>();

把数组的长度 length 存入到TreeMap的key中,value则存放 大小为 key 的数组剩余个数。

在取值时通过 ceilingKey 可以拿到 大小 >= 所需长度length的 TreeMap的 Key

再通过拿到的 TreeMap的 key 去 cache中获取 数组,,获取到数组后将TreeMap的key对应的value减一

put时----->同样将 数组 存入 cache缓存中, 同时将 TreeMap的对应key的value值 +1

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

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值