博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
越深入java 就觉得java做得越烂,java设计问题 之 : 对象占用内存空间设计
阅读量:2800 次
发布时间:2019-05-13

本文共 3156 字,大约阅读时间需要 10 分钟。

近段时间,项目要求对java的内存有要求,客户希望不要老是要他们扩大内存,所以此过程中了解了一些问题。 
越想觉得,java越不是。 
1,基础对象占有内存 byte,char,short,int,long,float,double分别为 1,2,2,4,8,4,8,byte; 
  包括后Byte,Short,Integer,Long....等分别为 16,16,16,16,都是byte 
  本来是 1字节的 byte包装后占 16字节!! 太不象话了,白用我的内存。除了一个Object 8byte指针其它浪费。 
2, Object 8byte指针,就算定义个空对象,也一样占8byte 我觉得一个指针要 8个字节吗?有必要吗?我的内存啊。 
  2^64= 18446744073709551616 byte =17179869184G 有可能用这么大的内存地址吗?(欢迎内行发言)。 
  个人觉得:6个byte足也,281474976710656 = 262144G 不知道有什么难处要用 8byte. 
3, Byte 用了 16字字节,真是想不通:8(指针)+8;浪费7byte 
4, Short用了 16字字节,真是想不通:8(指针)+8;浪费6byte 
5, Integer 用了 16字字节,真是想不通:8(指针)+8;浪费4byte 
6, Long    用了 16字字节,:8(指针)+8;没浪费。 
7, Float  用了 16字字节,真是想不通:8(指针)+8;浪费4byte。 
8, Double  用了 16字字节,:8(指针)+8;没浪费。 
9, BigDecimal  用了 32字字节,:8(指针)+24;除指针外 16不够? 太猛了吧?吃内存啊!!! 
10,object = new String();  用了 40 字字节,:8(指针)+32;好象内存没花钱一样。 
11 int[] a =new int[]{0};  也是16字节 
11 long[] a =new long[]{0};  也是24字节 
这么基础的东西,做得这样烂,java倒底怎么了? 难道为吃内存而生? 
现在知道,为什么java在游戏上插不上足,这样根本是不行的。 
不用对象,又难以区分数据库为空的数据,真是进退两难。 
为什么java不在新版本上来个新架构啊,这样下去只有一条:死......... 
本来用 byte 只需要 100M,如果用 Byte就要 1.6G 
(有多少米?内存地址能搞多大?32? 64?) 
本来用 int  只需要 400M,如果用 Integer就要 1.6G 
详细见:
1.3,1.4测试代码(1.5,1.6java本身有方法提供)
  1. import java.util.ArrayList;
  2. import java.math.BigDecimal;
  3. /**
  4.  * @author guishuanglin 2008-12-2 原程序作者:Vladimir Roubtsov
  5.  * 
  6.  */
  7. public class Sizeof {
  8.     public static void main(String[] args) throws Exception {
  9.         // Warm up all classes/methods we will use
  10.         runGC();
  11.         usedMemory();
  12.         // Array to keep strong references to allocated objects
  13.         final int count = 100000;
  14.         Object[] objects = new Object[count];
  15.         long heap1 = 0;
  16.         // Allocate count+1 objects, discard the first one
  17.         for (int i = -1; i < count; ++i) {
  18.             Object object = null;
  19.             // Instantiate your data here and assign it to object
  20.             // object = new Object();
  21.             // object = new Integer (i);
  22.             // object = new Long (i);
  23.             // object = new String ();
  24.             // object = new byte [128][1];
  25.             // object = new Float(1);
  26.             // object = new Double(1);
  27.             // object = new BigDecimal(1);
  28.             //object = new String();
  29.             //object = new StringBuffer();
  30.             //object = new Character('中');
  31.             if (i >= 0)
  32.                 objects[i] = object;
  33.             else {
  34.                 object = null// Discard the warm up object
  35.                 runGC();
  36.                 heap1 = usedMemory(); // Take a before heap snapshot
  37.             }
  38.         }
  39.         runGC();
  40.         long heap2 = usedMemory(); // Take an after heap snapshot:
  41.         final int size = Math.round(((float) (heap2 - heap1)) / count);
  42.         System.out.println("'before' heap: " + heap1 + ", 'after' heap: "
  43.                 + heap2);
  44.         System.out.println("heap delta: " + (heap2 - heap1) + ", {"
  45.                 + objects[0].getClass() + "} size = " + size + " bytes");
  46.         for (int i = 0; i < count; ++i)
  47.             objects[i] = null;
  48.         objects = null;
  49.     }
  50.     private static void runGC() throws Exception {
  51.         // It helps to call Runtime.gc()
  52.         // using several method calls:
  53.         for (int r = 0; r < 4; ++r)
  54.             _runGC();
  55.     }
  56.     private static void _runGC() throws Exception {
  57.         long usedMem1 = usedMemory(), usedMem2 = Long.MAX_VALUE;
  58.         for (int i = 0; (usedMem1 < usedMem2) && (i < 500); ++i) {
  59.             s_runtime.runFinalization();
  60.             s_runtime.gc();
  61.             Thread.currentThread().yield();
  62.             usedMem2 = usedMem1;
  63.             usedMem1 = usedMemory();
  64.         }
  65.     }
  66.     private static long usedMemory() {
  67.         return s_runtime.totalMemory() - s_runtime.freeMemory();
  68.     }
  69.     private static final Runtime s_runtime = Runtime.getRuntime();
  70. // End of class

转载地址:http://xdnmd.baihongyu.com/

你可能感兴趣的文章
实现了一个类似微信好有列表的控件
查看>>
实现了一个可以滚动的文字控件
查看>>
自己重新定义的一个窗口控件
查看>>
关于typedef的用法
查看>>
CentOS6.5系统挂载NTFS分区的移动硬盘
查看>>
配置 yum 源的两种方法
查看>>
Unique Paths II
查看>>
Minimum Path Sum
查看>>
Maximum Subarray
查看>>
ACE Lock类介绍
查看>>
ACE_Task介绍
查看>>
mmap分析
查看>>
搞了个LAMP,没事也整理个问题集
查看>>
给你一段文章,Apache的日志分割和虚拟主机你还能不会?
查看>>
搞了Apache,怎么可能不搞搞Nginx呢?
查看>>
javascript调用微软CertEnroll实现CSP数字证书申请
查看>>
cookie实现本地数据存储
查看>>
Spring Boot添加DB2驱动
查看>>
log4j2小试
查看>>
Apache HttpComponents 运用
查看>>