• Java内存操作知识汇总


    堆缓冲和直接缓冲区、

    堆内存可以使用工具VisualVM Launcher查看。

    其他内存监控工具

    直接缓冲区DIrect Buffers 又称堆外内存,本机内存,默认64M,可通过参数-XX:MaxDirectMemorySize指定。

    public static void test() {
            ByteBuffer buf=ByteBuffer.allocateDirect(2048);
            System.out.println(buf.position());
            System.out.println(buf.limit());
            System.out.println(buf.capacity());
            System.out.println(buf.isDirect());
        }
    /×
    0
    2048
    2048
    true
    
    ×/
    ByteBuffer分配直接内存

     运行jar包时,添加-XX:+PrintGCDetails可打印GC信息。其他参数信息

    堆外内存的释放

    系统释放

    Direct ByteBuffer 对象本身放在堆中,占用很小内存,关联对外内存。堆外内存使用过多,可能导致OutOfMemory错误。

     Direct ByteBuffer要full gc才能回收,所以如果堆内存用得少,堆外内存用得多,这样不触发full gc会导致堆外内存out of memory。

     ByteBuffer被GC,关联的对外内存也会被释放。当新生代满了,就会发生young gc;如果此时对象还没失效,就不会被回收;撑过几次young gc后,对象被迁移到老生代;当老生代也满了,就会发生full gc。

    主动释放

    使用sun.misc.Cleaner中的clean方法,参考文章

    import java.nio.ByteBuffer;
    import sun.nio.ch.DirectBuffer;
     
    public class DirectByteBufferCleaner {
     
            public static void clean(final ByteBuffer byteBuffer) {
                  if (byteBuffer.isDirect()) {
                     ((DirectBuffer)byteBuffer).cleaner().clean();
                  }
            }
    }
    
    public static void sleep(long i) {
        try {
              Thread.sleep(i);
         }catch(Exception e) {
              /*skip*/
         }
    }
    public static void main(String []args) throws Exception {
           ByteBuffer buffer = ByteBuffer.allocateDirect(1024 * 1024 * 100);
           System.out.println("start");
           sleep(10000);
           clean(buffer);
           System.out.println("end");
           sleep(10000);
    }
    cleaner释放对外内存

    本例中申请100M堆外内存,10s后释放。

    该博客有很多关于JVM的知识。

     该文章 对内存分配介绍

  • 相关阅读:
    Flask_脚本
    数据库
    模板
    视图函数和视图类
    HTTP请求
    Flask路由注册
    初识Flask
    微信小程序之基础使用
    celery任务队列
    文件处理小结
  • 原文地址:https://www.cnblogs.com/legion/p/8759475.html
Copyright © 2020-2023  润新知