在Java中没有sizeof运算符,所以没办法知道一个对象到底占用了多大的空间,但是在分配对象的时候会有一些基本的规则,我们根据这些规则大致能判断出来对象大小。

对象头

对象的头部至少有两个WORD,如果是数组的话,那么三个WORD,内容如下:

  1. 对象的HashCode,锁信息等
  2. 到对象类型数据的指针
  3. 数组的长度(如果是数组的话)

规则

首先,任何对象都是8字节对齐,属性按照[long,double]、[int,float]、[char,short]、[byte,boolean]、reference的顺序存放,举个例子:

public class Test {
    byte a;
    int b;
    boolean c;
    long d;
    Object e;
}

如果这个对象的属性按照顺序存放的话,要占用的空间为:head(8) + a(1) + padding(3) + b(4) + c(1) + padding(7) + d(8) + e(4) + padding(4) = 40。但是按照这个规则得到:head(8) + d(8) + b(4) + a(1) + c(1) + padding(2) + e(4) + padding(4) = 32。可以看到节省了不少空间。

在涉及继承关系的时候有一个最基本的规则:首先存放父类中的成员,接着才是子类中的成员,举个例子:

class A {
    long a;
    int b;
    int c;
}
class B extends A {
    long d;
}

这样存放的顺序及占用空间如下:head(8) + a(8) + b(4) + c(4) + d(8) = 32。那如果父类中的属性不够八个字节怎么办?这样就有了新的一条规则:父类中最后一个成员与子类的第一个成员的间隔如果不够4个字节,此时需要扩展到4个字节的基本单位,举个例子:

class A {
    byte a;
}
class B extends A {
    byte b;
}

那么此时占用的空间如下:head(8) + a(1) + padding(3) + b(1) + padding(3) = 16。显然这种方式比较浪费空间,那么就有了:如果子类的第一个成员是double或者long,并且父类并没有用完8个字节,JVM会破坏规将较小的数据填充到该空间,举个例子:

class A {
    byte a;
}
class B extends A {
    long b;
    short c;
    byte d;
}

此时占用的空间如下:head(8) + a(1) + padding(3) + c(2) + d(1) + padding(1) + b(8) = 24。

如何计算Java对象占用了多少空间?的更多相关文章

  1. 如何计算Java对象所占内存的大小

    [ 简单总结: 随便一个java项目,引入jar包: lucene-core-4.0.0.jar 如果是 maven项目,直接用如下依赖: <dependency> <groupId ...

  2. java.lang.instrument: 一个Java对象占用多少字节?

    一.对象头包括两部分信息:Mark Word(标记字段)和 Klass Pointer(类型指针)   1. Mark Word 用于存储对象自身的运行时数据,如哈希码(HashCode).GC分代年 ...

  3. java 对象占用内存

    String 方法用于文本分析及大量字符串处理时会对内存性能造成一些影响.可能导致内存占用太大甚至OOM. 一.先介绍一下String对象的内存占用 一般而言,Java 对象在虚拟机的结构如下:•对象 ...

  4. 高端面试必备:一个Java对象占用多大内存

    这个问题一般会出现在稍微高端一点的 Java 面试环节.要求面试者不仅对 Java 基础知识熟悉,更重要的是要了解内存模型. Java 对象模型 HotSpot JVM 使用名为 oops (Ordi ...

  5. 获取JAVA对象占用的内存大小

    介绍两种获取JAVA对象内存大小的方法. 第一种:Instrumentation 简介: 使用java.lang.instrument 的Instrumentation来获取一个对象的内存大小.利用I ...

  6. java对象占用内存大小计算方式

    案例一: User public class User { } UserSizeTest public class UserSizeTest { static final Runtime runTim ...

  7. java 对象占用内存查看 以及JVM级别 方法修改等

    public interface Instrumentation 此类提供检测 Java 编程语言代码所需的服务.检测是向方法中添加字节码,以搜集各种工具所使用的数据.由于更改完全是进行添加,所以这些 ...

  8. 计算Java对象内存大小

    摘要 本文以如何计算Java对象占用内存大小为切入点,在讨论计算Java对象占用堆内存大小的方法的基础上,详细讨论了Java对象头格式并结合JDK源码对对象头中的协议字段做了介绍,涉及内存模型.锁原理 ...

  9. 一个Java对象到底占用多大内存?

    最近在读<深入理解Java虚拟机>,对Java对象的内存布局有了进一步的认识,于是脑子里自然而然就有一个很普通的问题,就是一个Java对象到底占用多大内存? 在网上搜到了一篇博客讲的非常好 ...

随机推荐

  1. 转载:C#之接口简介

    原文地址 http://www.cnblogs.com/michaelxu/archive/2007/03/29/692021.html 感谢博主分享! 什么是接口?其实,接口简单理解就是一种约定,使 ...

  2. 开始学习编程了…… 2015年九月七日 …… 31岁的Me.

    给自己下的命令:做今天开始认认真真地开始学习编程,一年后的今天一定要找到一份编程的工作. 为什么要学编程?:因为不想回以前的圈子,“创业”快三年什么都给“创”没了,咳……,不过呢,倒是领略到编程能带来 ...

  3. 动态的显示当前的时间---setInterval的用法

    <!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8&quo ...

  4. 无法在web服务器上启动调试。调试失败,因为没有启用集成windows身份验证

    ----注意:以管理员身份运行VS C#中ASP.NET Web应用程序编译时的错误:无法在web服务器上启动调试.调试失败,因为没有启用集成windows身份验证. 解决:打开IIS,在IIS里查看 ...

  5. struts2与spring整合问题,访问struts2链接时,spring会负责创建Action

    每次访问一次链接,spring会创建一个对象,并将链接所带的参数注入到Action的变量中(如何做到的呐) 因为: struts2的action每次访问都重新创建一个对象,那spring的ioc是怎么 ...

  6. 【转】 HVTableView创建--展开/折叠列表能 AAShareBubbles社会分享动画组

    原文: http://blog.csdn.net/billfanggs/article/details/17279969 HVTableView HVTableView是UITableView(带有展 ...

  7. 【COGS 56】质数取石子

    [问题描述] DD 和 MM 正在玩取石子游戏.他们的游戏规则是这样的:桌上有若干石子,DD 先取,轮流取,每次必须取质数个.如果某一时刻某一方无法从桌上的石子中取质数个,比如说剩下 0 个或 1 个 ...

  8. 安卓应用开发用户体验之禁止EditText自动获取焦点

    一.问题描述: 在安卓应用开发时,经常会在同一个页面有许多不同的控件,在用户操作时,如何正确的在这些控件之间来回切换是良好用户体验的重要问题.可能会碰到如下问题:在点击页面内某控件时(假设控件为Spi ...

  9. int, NSInteger, NSUInteger, NSNumber的区别

    新手在接触iOS或者Mac开发的时候,看到int和NSInteger,一般不清楚应该用哪个比较合适.我们先来查看下NSInteger的定义 #if __LP64__ || (TARGET_OS_EMB ...

  10. 『重构--改善既有代码的设计』读书笔记----Split Temporary Variable

    继续开始我们重构手法的系列,今天介绍的是Split Temporary Variable---分解临时变量. 在我们平常写的程序中肯定有某些临时变量被赋予了超过一个的责任.如果他们不是那种收集结果(t ...