0、说明

根据算法书上的定义,一个算法的空间复杂度包括算法程序所占用的空间,输入初始数据所占用的空间以及算法执行过程中所需要的额外空间。
本文各种结论全部参考过标准文献,本人也进行过验证。验证过程本文不做说明。例如:当前主流虚拟机boolean类型运行时确实是1字节。
部分与计算空间无关的细节也不做说明,例如:对象头具体包含哪些信息、分别在哪几位、什么是指针压缩等。
细节信息,本人以后会在《JVM浅析》栏目中一一补充,敬请期待哦~

一、基础知识

1. 数据类型以及大小

  基本类型
类型名称 占用字节数
 boolean  1
 byte  1
 char  2
 short  2
 int  4
 float  4
 long  8
 double  8
  引用类型
 操作系统位数  占用字节数
 32位  4
 64位  8 (指针压缩后4字节)

*注:引用类型(注意是引用类型变量,不是对象实例,本质上是指针,其中数组类型变量也属于引用类型变量)。

2. 内存计算公式

对象占用内存 = 对象头开销 + 实例数据(如果是引用类型则包括 变量 和 实例 两部分开销) + 填充数据。

a.对象头开销

指向类引用、垃圾收集信息、同步信息等。
32位JVM 对象头8字节,数组对象头16字节。
64位JVM 对象头16字节(指针压缩后12字节),数组对象头24字节(指针压缩后16字节)。
空对象 / 空数组 都只有对象头。

b.实例数据

基本类型在内存只有值所占用空间大小。
引用类型包含 变量 和 值 两部分占用空间大小(引用变量就相当于指针,用一个系统存储单元存储。值则是堆中实例的大小)。

c.填充数据

hotspot JVM里,对象占用空间是8字节对齐的。因为在内存中一个存储单元是8字节的。
意思是一个Java对象使用的内存一定是8字节的整数倍,如果通过计算后发现对象所需内存不是8字节的整数倍,则会将其填充为8字节的倍数。
例如:对象实例可能需要内存为30字节或者28字节等,都会被填充为32字节。

d.继承关系(不计算父类对象头开销)

子类对象占用内存 = 子类对象头开销 + 子类实例数据 + (父类实例数据+填充数据) + 填充数据。

二、计算实例

因为现在主流都是64位系统,下面测试类会按照64位环境计算内存。并且没有考虑指针压缩的情况。
测试类演示了最复杂的情况,只为演示计算过程,命名不规范,请勿在实际项目中模仿。

new B()总共占用内存空间 = [ (4(a) + 2(bs) + 2(填充数据)) + 4(ba) + 8(cs数组引用变量) + 4(填充数据) ] + [ 24(cs数组对象头) + 3(cs数组内引用变量个数,即cs[0]、cs[1]、cs[2]) * 8(cs数组中引用变量占用内存) ] + [ (16(C实例字节头信息) + 1(c变量) + 7(填充字节)) * 3(C实例数量) ] = 144字节(8字节的整数倍)。

备注

64位JVM才会有指针压缩的情况。-XX:+UseCompressedOops(开启)  -XX:-UseCompressedOops(关闭)。
JDK1.6以后才加入此项功能并且默认开启指针压缩。但计算公式不变,只是有些对象占用内存数值会变。大家自行计算压缩指针后或者32位JVM下的占用内存。

查看指针压缩等虚拟机参数信息可用如下两个命令:
jcmd    //查看进程信息 (数字列显示的是PID,要保证程序在运行过程中,想测试的话可以到公司服务器上查看)。
jcmd [PID] VM.flags    //查看该pid对应进程设置的JVM参数。

算法复杂度之 空间复杂度(Java)的更多相关文章

  1. 【java】之算法复杂度o(1), o(n), o(logn), o(nlogn)

    在描述算法复杂度时,经常用到o(1), o(n), o(logn), o(nlogn)来表示对应算法的时间复杂度, 这里进行归纳一下它们代表的含义: 这是算法的时空复杂度的表示.不仅仅用于表示时间复杂 ...

  2. Python语言算法的时间复杂度和空间复杂度

    算法复杂度分为时间复杂度和空间复杂度. 其作用: 时间复杂度是指执行算法所需要的计算工作量: 而空间复杂度是指执行这个算法所需要的内存空间. (算法的复杂性体现在运行该算法时的计算机所需资源的多少上, ...

  3. C#中常用的排序算法的时间复杂度和空间复杂度

    常用的排序算法的时间复杂度和空间复杂度   常用的排序算法的时间复杂度和空间复杂度 排序法 最差时间分析 平均时间复杂度 稳定度 空间复杂度 冒泡排序 O(n2) O(n2) 稳定 O(1) 快速排序 ...

  4. 有N个正实数(注意是实数,大小升序排列) x1 , x2 ... xN,另有一个实数M。 需要选出若干个x,使这几个x的和与 M 最接近。 请描述实现算法,并指出算法复杂度

    题目:有N个正实数(注意是实数,大小升序排列) x1 , x2 ... xN,另有一个实数M. 需要选出若干个x,使这几个x的和与 M 最接近. 请描述实现算法,并指出算法复杂度. 代码如下: #in ...

  5. js算法初窥07(算法复杂度)

    算法复杂度是我们来衡量一个算法执行效率的一个度量标准,算法复杂度通常主要有时间复杂度和空间复杂度两种.时间复杂度就是指算法代码在运行最终得到我们想要的结果时所消耗的时间,而空间复杂度则是指算法中用来存 ...

  6. o(1), o(n), o(logn), o(nlogn)算法复杂度

    在描述算法复杂度时,经常用到o(1), o(n), o(logn), o(nlogn)来表示对应算法的时间复杂度, 这里进行归纳一下它们代表的含义: 这是算法的时空复杂度的表示.不仅仅用于表示时间复杂 ...

  7. php算法基础----时间复杂度和空间复杂度

    算法复杂度分为时间复杂度和空间复杂度. 其作用: 时间复杂度是指执行算法所需要的计算工作量: 而空间复杂度是指执行这个算法所需要的内存空间. (算法的复杂性体现在运行该算法时的计算机所需资源的多少上, ...

  8. C数据结构与算法-算法复杂度

    算法复杂度分为时间复杂度T(n)和空间复杂度F(n) 时间复杂度:也就是执行算法程序所需的时间,与硬件的速度.编程语言的级别.编译器的优化.数据的规模.执行的频度有关,前三个有很大的不确定性,所以衡量 ...

  9. 数据结构和算法(Golang实现)(9)基础知识-算法复杂度及渐进符号

    算法复杂度及渐进符号 一.算法复杂度 首先每个程序运行过程中,都要占用一定的计算机资源,比如内存,磁盘等,这些是空间,计算过程中需要判断,循环执行某些逻辑,周而反复,这些是时间. 那么一个算法有多好, ...

随机推荐

  1. 从零学React Native之07View

    View 组件是React Native最基本的组件.绝大部分其他React Native 组件. View组件的颜色和边框 backgroundColor 键用来指定颜色. RN 0.19版本开始, ...

  2. VS开发ArcEngine时的一个异常信息——“ArcGIS version not specified. You must call RuntimeManager.Bind before creating any ArcGIS components.”

    问题描述:程序报错“ArcGIS version not specified. You must call RuntimeManager.Bind before creating any ArcGIS ...

  3. 2019-10-22-Roslyn-打包自定义的文件到-NuGet-包

    title author date CreateTime categories Roslyn 打包自定义的文件到 NuGet 包 lindexi 2019-10-22 19:45:34 +0800 2 ...

  4. Python基础:04映射类型

    字典是Python语言中唯一的映射类型.一个字典对象是可变的,它是一个容器类型,能存储任意个数的Python对象.字典中的数据是无序排列的. 映射类型也可被称做哈希表,哈希表的算法是获取键,对键执行一 ...

  5. Mac OSX原生读写NTFS功能开启方法

    macOX系统内建的NTFS支持默认只能读不能写 原生读写NTFS,需要自行终端命令手动开启 1. 插上磁盘 此时Mac桌面应该会显示出插入的磁盘,但是当你想把文件拖入磁盘的时候,发现是不能拖进去的, ...

  6. Linux 网络原理及基础设置

    临时配置网络(ip,网关,dns)+永久配置 设置IP和掩码 ifconfig eth0 192.168.2.2 netmask 255.255.255.0 设置网关route add default ...

  7. 怎么查看mysql 的binlog日志存放的位置

    image.png 这个你可以看配置文件 启用了才有这样的记录默认是没有的 linux系统中的/etc/my.cnf my.cnf内容: log-bin = mysqlbin # 默认配置 一般放在/ ...

  8. JS iFrame 加载慢怎么解决

    在项目中经常要动态添加iframe,然后再对添加的iframe进行相关操作,有时候会遇到iframe加载很慢什么原因呢,该如何解决呢?带着这个问题一起通过本文学习,寻找答案吧! aaa.html &l ...

  9. ifram子页面与父页面的方法相互调用

    parent.html <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http:/ ...

  10. [转][ASP.NET Core 3框架揭秘] 跨平台开发体验: Windows [上篇]

    微软在千禧年推出 .NET战略,并在两年后推出第一个版本的.NET Framework和IDE(Visual Studio.NET 2002,后来改名为Visual Studio),如果你是一个资深的 ...