一、什么是堆,它和栈有什么区别?
1、变量和堆的关系

package heap;public class Test01 {public static void test() {int j = 100;}public static void main(String[] args) {int i = 10;test();}
}

以上代码的执行顺序:
(1)main方法,java虚拟机栈开辟了一个栈帧,存放变量int i = 10
(2)执行到test方法时,java虚拟机栈新开辟一个栈帧,存放变量int j = 100
(3)test方法执行完后,test栈帧被回收(后进先出),但是main栈帧没执行完就没回收

方法的变量和堆没有关系,存储在栈帧里

2、数组和堆的关系

package heap;public class Test02 {public static void main(String[] args) {int[] x = new int[5];x[0] = 100;x = null;}
}

以上代码的执行顺序:
(1)执行main方法,java虚拟机栈开辟了一个栈帧。
当执行int[] x = new int[5]时,栈开辟了x变量空间,该变量存放的是堆的引用地址。
堆开辟了x数组空间,例如0x0001,存放数组的值。数组的元素都设置默认值0.
栈里的x存放的是堆的引用地址,例如x = 0x0001。
(2)执行x[0]=100时,
堆会为x[0]=100,栈的x变量不会变,继续引用堆的地址。

(3)当执行x=null时,x引用的内存地址被删除,例如栈帧删除了0x0001。而堆中的数组不再被x使用后,就会变成垃圾,堆不会立即删除,它是采用垃圾回收算法删除。

package heap;public class Test03 {public static void main(String[] args) {int[] x = new int[5];x[0] = 100;int y[] = x;x = null;}
}

以上代码:
(4)当执行了int[] y = x时,栈开辟了y变量空间,该变量存放的是堆的引用地址0x0001。即y和x一样都是引用同一个地址。
当执行x=null时,x引用的内存地址被删除。但堆中的0x0001仍然被y引用,堆中的数据会一直存在,不会被垃圾回收算法删除。

3、对象和堆的关系

package heap;public class Test04 {public static void main(String[] args) {Book book1 = new Book("java", "aaa");Book book2 = new Book("jvm", "bbb");}public static class Book {private String name;private String author;public Book(String name, String author) {this.name = name;this.author = author;}public String getName() {return name;}public void setName(String name) {this.name = name;}public String getAuthor() {return author;}public void setAuthor(String author) {this.author = author;}}
}

以上代码:
定义了2个对象,栈开辟了2个空间存放堆的地址,堆开辟了2个空间存储数据。
只要每次new一个对象,堆都会为对象分配空间存储。

4、总结
栈:
(1)基本数据类型、局部变量存放在栈帧内,方法执行完毕(栈帧出栈)立即释放,节约空间。
(2)栈帧内的变量,没有默认值,需要手工设置。(方法里的变量是没有默认值)
(3)栈帧只存留在单个线程中,其他线程访问不了。
(4)可以使用-Xss来定义栈内存大小。
(5)当堆栈内存已满时,Java运行时抛出java.lang.StackOverFlowError
堆:
(1)数组和对象存于堆中,用完后(栈帧不再引用),靠垃圾回收算法清除。
(2)堆内对象的变量都有默认值。
(3)所有的线程共享堆,即所有栈帧的变量都能引用堆的内存地址。
(4)可以使用-Xms和-Xmx的JVM选项来定义堆内存的启动大小和最大大小。
(5)如果堆内存已满,则抛出java.lang.OutOfMemoryError

二、什么是短命对象,什么是长命对象

package heap;import java.util.ArrayList;
import java.util.List;public class Father {private List<Son> sons = new ArrayList<Son>();public Son giveSon(String name) {return new Son(name);}public static void main(String[] args) {Father father = new Father();Son a = father.giveSon("a");father.sons.add(a);father.giveSon("b");}
}

1、长命对象
一直有人引用就是长命对象
(1)栈一直引用,例如main函数一直运行,它的对象father就一直存活。
(2)栈帧出栈后,对象被其他对象引用,例如giveSon("a"),出栈后被sons引用。
2、短命对象
没人引用就是短命对象,也称为垃圾对象,因为没人用它,即没人引用它,例如giveSon("b")出栈后里面的son没人引用,就变成垃圾了。
3、在JVM中,大部分都是短命对象;少数对象长期存活,例如main函数的栈一直引用father,Father的sons一直引用son a。

三、为什么要设计分代模型:年轻代和老年代

1、什么是分代模型
分代模型:把堆分为年轻代、老年代
年轻代:存储短命对象
老年代:存储长命对象

2、为什么要这么设计
因为来源于生活,例如:
生活垃圾放在垃圾桶(年轻代),因为生活垃圾对你没用,所以拿个垃圾桶存起来。
钻石黄金存放到保险柜(老年代),因为钻石黄金对太多人有用了,所以拿个保险柜保存起来。
如果不设计分代,那钻石黄金和生活垃圾就放在一起了,乱套了。

四、基于参数设置jvm内存空间
1、如何查看当前堆的大小

package heap;import com.sun.management.OperatingSystemMXBean;
import java.lang.management.ManagementFactory;public class TestB01 {public static void main(String[] args) {int byteToMb = 1024 * 1024;long totalMemory = Runtime.getRuntime().totalMemory() / byteToMb;long maxMemory = Runtime.getRuntime().maxMemory() / byteToMb;System.out.println("当前初始内存大小 -Xms :" + totalMemory + "MB");System.out.println("当前最大内存大小 -Xmx :" + maxMemory + "MB");//操作系统级内存情况查询OperatingSystemMXBean osmxb = (OperatingSystemMXBean) ManagementFactory.getOperatingSystemMXBean();long physicalFree = osmxb.getFreePhysicalMemorySize() / byteToMb;long physicalTotal = osmxb.getTotalPhysicalMemorySize() / byteToMb;long physicalUse = physicalTotal - physicalFree;System.out.println("操作系统物理内存已用空间:" + physicalUse + "MB");System.out.println("操作系统物理内存空闲空间:" + physicalFree + "MB");System.out.println("操作系统总物理内存大小:" + physicalTotal + "MB");System.out.println("默认堆 初始内存大小:物理电脑内存大小 / 64 = " + physicalTotal / 64 + "MB");System.out.println("默认堆 最大内存大小:物理电脑内存大小 / 4 = " + physicalTotal /4 + "MB");}
}

2、通过参数,自定义堆内存大小
堆的大小在jvm启动时就已经设定好了,可以通过“-Xms”和“-Xmx”来进行设置:
(1)-X是jvm的运行参数
(2)“-Xms”用于表示堆区的起始内存,ms是memory start
(3)“-Xmx”用于表示堆区的最大内存,比如手动设置:-Xms512m -Xmx512m

五、基于jmap剖析堆的内部结构
1、jmap命令
jmap命令是一个可以输出所有内存中对象的工具,甚至可以将VM中的heap,以二进制输出成文本。
打印出某个java进程(使用pid)内存内的,所有“对象”的情况(如:产生那些对象,及其数量)。

2、采用springboot来试验

jmap -heap 32594
Attaching to process ID 32594, please wait...
Debugger attached successfully.
Server compiler detected.
JVM version is 25.231-b11using thread-local object allocation.
Parallel GC with 2 thread(s)Heap Configuration:MinHeapFreeRatio         = 0MaxHeapFreeRatio         = 100MaxHeapSize              = 1073741824 (1024.0MB)NewSize                  = 357564416 (341.0MB)MaxNewSize               = 357564416 (341.0MB)OldSize                  = 716177408 (683.0MB)NewRatio                 = 2SurvivorRatio            = 8MetaspaceSize            = 21807104 (20.796875MB)CompressedClassSpaceSize = 1073741824 (1024.0MB)MaxMetaspaceSize         = 17592186044415 MBG1HeapRegionSize         = 0 (0.0MB)Heap Usage:
PS Young Generation
Eden Space:capacity = 290455552 (277.0MB)used     = 44679448 (42.609642028808594MB)free     = 245776104 (234.3903579711914MB)15.382542248667363% used
From Space:capacity = 33030144 (31.5MB)used     = 4053248 (3.865478515625MB)free     = 28976896 (27.634521484375MB)12.271360367063492% used
To Space:capacity = 33554432 (32.0MB)used     = 0 (0.0MB)free     = 33554432 (32.0MB)0.0% used
PS Old Generationcapacity = 716177408 (683.0MB)used     = 43105960 (41.109046936035156MB)free     = 673071448 (641.8909530639648MB)6.01889413411935% used32413 interned Strings occupying 3173232 bytes.

Parallel GC with 2 thread(s):采用并行垃圾收集器
MinHeapFreeRatio:JVM最小空闲比率,可由-XX:MinHeapFreeRatio=<n>参数设置,jvm heap 在使用率小于n时,heap进行收缩
MaxHeapFreeRatio:JVM最大空闲比率,可由-XX:MaxHeapFreeRatio=<n>参数设置,jvm heap 在使用率大于n时,heap进行扩张
MaxHeapSize:JVM堆的最大大小,可由-XX:MaxHeapSize=<n>参数设置
NewSize:JVM新生代的默认大小,可由-XX:NewSize=<n>参数设置
MaxNewSize:JVM新生代的最大大小,可由-XX:MaxNewSize=<n>参数设置
OldSize:JVM老生代的默认大小,可由-XX:OldSize=<n>参数设置
NewRatio:新生代:老生代(的大小)= 1:2,可由-XX:NewRatio=<n>参数指定New Generation与Old Generation heap size的比例
SurvivorRatio:survivor:eden = 1:8,即survivor space是新生代大小的1/(8+2),[因为有两个survivor区域],可由-XX:SurvivorRatio=<n>参数设置
PS:survivor和eden是新生代里面的东西
MetaspaceSize:元空间的默认大小,超过此值就会触发Full GC,可由-XX:MetaspaceSize=<n>参数设置
CompressedClassSpaceSize:类指针压缩空间的默认大小,可由-XX:CompressedClassSpaceSize=<n>参数设置
MaxMetaspaceSize:元空间的最大大小,可由-XX:MaxMetaspaceSize=<n>参数设置
G1HeapRegionSize:使用G1垃圾收集器的时候,堆被分割的大小,可由-XX:G1HeapRegionSize=<n>参数设置

PS Young Generation:新生代内存分布,包含eden区和survivor区
Eden Space:eden区内存
From Space:survivor区的from内存
To Space:survivor区的to内存
PS Old Generation:老生代区内存

3、堆的大小

4、总结
(1)java的堆是按照垃圾收集器来设计的。目前主流的垃圾收集器G1,分代设计的垃圾收集器主要是CMS、G1。
(2)堆的分代设计,就是把一块内存划分为多块。
(3)堆的内存空间分配主要是分为2块,年轻代和老年代。
(4)年轻代和老年代的比例是1:2,可采用-X:NewRatio=<n>来调节设置。
(5)年轻代分为Eden和Survivor From、Survivor To的大小比例是8:1:1,可采用-XX:SurvivorRatio=<n>来调节设置。

六、如何读懂gc日志
1、参数说明
-Xms30M -Xmx30M:年轻代10M,老年代20M
-XX:+PrintGCDetails(jdk11废弃,换成-Xlog:gc*):输出GC的详细日志
-XX:+PrintHeapAtGC(jdk11废弃,换成-Xlog:gc+heap=trace):打印出触发GC之前、之后的日志

package heap;public class GcTest01 {private static final int _1MB = 1024 * 1024;/**-Xms30M-Xmx30M-XX:+PrintGCDetails(jdk11废弃,换成-Xlog:gc*)-XX:+PrintHeapAtGC(jdk11废弃,换成-Xlog:gc+heap=trace)*/public static void main(String[] args) throws InterruptedException {byte[] allocation, allocation2, allocation3, allocation4;allocation = new byte[8*_1MB];System.out.println("----------创建8M后----------");allocation2 = new byte[8*_1MB];System.out.println("----------创建8M后----------");allocation3 = new byte[8*_1MB];System.out.println("----------创建8M后----------");}
}

执行结果:

----------创建8M后----------
----------创建8M后----------
{Heap before GC invocations=1 (full 0):PSYoungGen      total 9216K, used 2023K [0x00000000ff600000, 0x0000000100000000, 0x0000000100000000)eden space 8192K, 24% used [0x00000000ff600000,0x00000000ff7f9d30,0x00000000ffe00000)from space 1024K, 0% used [0x00000000fff00000,0x00000000fff00000,0x0000000100000000)to   space 1024K, 0% used [0x00000000ffe00000,0x00000000ffe00000,0x00000000fff00000)ParOldGen       total 20480K, used 16384K [0x00000000fe200000, 0x00000000ff600000, 0x00000000ff600000)object space 20480K, 80% used [0x00000000fe200000,0x00000000ff200020,0x00000000ff600000)Metaspace       used 3297K, capacity 4496K, committed 4864K, reserved 1056768Kclass space    used 358K, capacity 388K, committed 512K, reserved 1048576K
[GC (Allocation Failure) [PSYoungGen: 2023K->840K(9216K)] 18407K->17232K(29696K), 0.0005962 secs] [Times: user=0.00 sys=0.00, real=0.00 secs]
Heap after GC invocations=1 (full 0):PSYoungGen      total 9216K, used 840K [0x00000000ff600000, 0x0000000100000000, 0x0000000100000000)eden space 8192K, 0% used [0x00000000ff600000,0x00000000ff600000,0x00000000ffe00000)from space 1024K, 82% used [0x00000000ffe00000,0x00000000ffed2020,0x00000000fff00000)to   space 1024K, 0% used [0x00000000fff00000,0x00000000fff00000,0x0000000100000000)ParOldGen       total 20480K, used 16392K [0x00000000fe200000, 0x00000000ff600000, 0x00000000ff600000)object space 20480K, 80% used [0x00000000fe200000,0x00000000ff202020,0x00000000ff600000)Metaspace       used 3297K, capacity 4496K, committed 4864K, reserved 1056768Kclass space    used 358K, capacity 388K, committed 512K, reserved 1048576K
}
......

2、触发了Young GC
[GC (Allocation Failure) [PSYoungGen: 2023K->840K(9216K)] 18407K->17232K(29696K), 0.0005962 secs] [Times: user=0.00 sys=0.00, real=0.00 secs] 
说明:
(1)GC (Allocation Failure):对象分配失败,此时就要触发一次Young GC
年轻代(Eden区和From区)内存不足,所以触发了Young GC

(2)PSYoungGen: 2023K->840K(9216K):
(9216K):年轻代可用空间是9216KB,也就是9MB。Eden区是8M,两个Survivor中只有一个是可以放存活对象的,另外一个是必须一直保持空闲的,所以它考虑年轻代的可用空间,就是1个Eden + 1个Survivor - from的大小,也就是9MB。
2023K->840K:意思是对年轻代执行了一次GC,GC之前都使用了2023KB了,但是GC之后只有840KB的对象是存活下来

(3)18407K->17232K(29696K)
18407K:GC前堆内存占用
17232K:GC后堆内存占用
29696K:堆内存总量

(4)0.0005962 secs
这个就是本次gc耗费的时间,大概耗费了0.6ms,仅仅是回收1.2MB的对象而已。

3、触发了GC前后
从执行结果看出,触发前内存占用Eden区。触发垃圾回收后,Eden区清空,From区填满了,老年代也使用了。

Heap after GC invocations=1 (full 0):PSYoungGen      total 9216K, used 840K [0x00000000ff600000, 0x0000000100000000, 0x0000000100000000)eden space 8192K, 0% used [0x00000000ff600000,0x00000000ff600000,0x00000000ffe00000)from space 1024K, 82% used [0x00000000ffe00000,0x00000000ffed2020,0x00000000fff00000)to   space 1024K, 0% used [0x00000000fff00000,0x00000000fff00000,0x0000000100000000)ParOldGen       total 20480K, used 16392K [0x00000000fe200000, 0x00000000ff600000, 0x00000000ff600000)object space 20480K, 80% used [0x00000000fe200000,0x00000000ff202020,0x00000000ff600000)Metaspace       used 3297K, capacity 4496K, committed 4864K, reserved 1056768Kclass space    used 358K, capacity 388K, committed 512K, reserved 1048576K

说明:
(1)PSYoungGen中最前面的PS代表垃圾收集器是Parallel垃圾收集器,回收的区域是新生代YoungGen。

(2)ParOldGen中最前面的Par代表垃圾收集器是Parallel Old收集器,回收的区域是老年代OldGen。

(3)Metaspace是元数据空间和Class空间,存放一些类信息、常量池这类的东西。

七、为什么内存看似够但触发了young gc
因为在启动jvm的时候,jvm自身自带了初始化对象占用了空间。
JVM启动的时候,就必须占用了3351K,3351K是系统自带的。

package heap;public class GcTest02 {public static void jp(String[] args) throws InterruptedException {Thread.sleep(1000000000);}
}

1、3351K是什么对象?
采用jmap -histo:live命令来查看
说明:
histo:live代表查看当前jvm存活的对象
jmap -histo:live 20504

 num     #instances         #bytes  class name
----------------------------------------------1:          4559         435672  [C2:           419         135984  [B3:          4410         105840  java.lang.String4:           706          80880  java.lang.Class5:           632          41512  [Ljava.lang.Object;6:           791          31640  java.util.TreeMap$Entry7:           628          25120  java.util.LinkedHashMap$Entry8:           426          18992  [Ljava.lang.String;9:           373          11936  java.util.HashMap$Node10:            24           8640  [Ljava.util.HashMap$Node;11:           113           8136  java.lang.reflect.Field12:           135           7720  [I13:            87           5568  java.net.URL14:           110           4400  java.lang.ref.SoftReference15:           256           4096  java.lang.Integer16:           121           3872  java.util.Hashtable$Entry17:           105           3360  java.util.concurrent.ConcurrentHashMap$Node18:             8           3008  java.lang.Thread19:            42           2352  sun.misc.URLClassPath$JarLoader20:            26           2080  java.lang.reflect.Constructor21:            16           2048  [Ljava.util.concurrent.ConcurrentHashMap$Node;22:            39           1872  sun.util.locale.LocaleObjectCache$CacheEntry23:            43           1720  java.lang.ref.Finalizer24:            34           1632  java.util.HashMap25:             1           1568  [[B26:            37           1480  java.io.ObjectStreamField27:            26           1456  java.lang.Class$ReflectionData28:            89           1424  java.lang.Object29:            20           1280  java.util.concurrent.ConcurrentHashMap30:            15           1200  [Ljava.util.WeakHashMap$Entry;31:             9           1184  [Ljava.util.Hashtable$Entry;32:             2           1064  [Ljava.lang.invoke.MethodHandle;33:             1           1040  [Ljava.lang.Integer;34:             1           1040  [[C35:            41            984  java.io.ExpiringCache$Entry36:            15            840  sun.nio.cs.UTF_8$Encoder37:            12            768  java.util.jar.JarFile38:            19            760  sun.util.locale.BaseLocale$Key39:            15            720  java.util.WeakHashMap40:            22            704  java.lang.ref.ReferenceQueue41:             7            672  java.util.jar.JarFile$JarFileEntry42:            12            672  java.util.zip.ZipFile$ZipFileInputStream43:            11            648  [Ljava.lang.reflect.Field;44:             8            640  [S45:            19            608  java.io.File46:            19            608  java.util.Locale47:            19            608  sun.util.locale.BaseLocale48:            13            520  java.security.AccessControlContext49:            21            504  java.util.jar.Attributes$Name50:            19            456  java.util.Locale$LocaleKey51:            18            432  sun.misc.MetaIndex52:            10            400  java.io.FileDescriptor53:            10            400  sun.nio.cs.UTF_8$Decoder54:            13            392  [Ljava.io.ObjectStreamField;55:             1            384  com.intellij.rt.execution.application.AppMainV2$156:             1            384  java.lang.ref.Finalizer$FinalizerThread57:            24            384  java.lang.ref.ReferenceQueue$Lock58:             6            384  java.nio.DirectByteBuffer59:            12            384  java.util.zip.ZipCoder60:             1            376  java.lang.ref.Reference$ReferenceHandler61:            18            352  [Ljava.lang.Class;62:             6            336  java.nio.DirectLongBufferU63:            10            320  java.lang.OutOfMemoryError64:             3            312  [D65:             2            312  [J66:            13            312  [Ljava.lang.reflect.Constructor;67:            13            312  sun.reflect.NativeConstructorAccessorImpl68:            12            288  java.util.ArrayDeque69:             5            280  sun.util.calendar.ZoneInfo70:             3            264  java.lang.reflect.Method71:            11            264  java.net.StandardSocketOptions$StdSocketOption72:            11            264  java.util.ArrayList73:             8            256  java.util.Vector74:             3            240  [Ljava.lang.ThreadLocal$ThreadLocalMap$Entry;75:             5            240  java.util.Hashtable76:             6            240  java.util.WeakHashMap$Entry77:             7            224  java.lang.ThreadLocal$ThreadLocalMap$Entry78:             4            224  java.util.LinkedHashMap79:             9            216  java.util.LinkedList$Node80:            13            208  sun.reflect.DelegatingConstructorAccessorImpl81:             5            200  java.security.ProtectionDomain82:             6            192  java.io.FileInputStream83:             4            192  java.util.Properties84:             4            192  java.util.TreeMap85:             2            160  [[Ljava.lang.String;86:             4            160  java.lang.ClassLoader$NativeLibrary87:             5            160  java.security.CodeSource88:             5            160  java.util.LinkedList89:             5            160  sun.util.locale.provider.LocaleProviderAdapter$Type90:             3            144  java.nio.HeapByteBuffer91:             6            144  sun.misc.PerfCounter92:             3            144  sun.misc.URLClassPath93:             2            128  java.io.ExpiringCache$194:             4            128  java.util.Stack95:             2            128  sun.nio.cs.ext.DoubleByte$Encoder96:             1            120  java.net.SocksSocketImpl97:             5            120  java.util.Collections$UnmodifiableRandomAccessList98:             5            120  sun.misc.FloatingDecimal$PreparedASCIIToBinaryBuffer99:             2            112  java.lang.Package100:             7            112  java.util.HashSet101:             2            112  java.util.ResourceBundle$CacheKey102:             2            112  java.util.zip.ZipFile$ZipFileInflaterInputStream103:             2            112  sun.nio.cs.ext.DoubleByte$Decoder104:             3             96  java.io.FileOutputStream105:             4             96  java.lang.RuntimePermission106:             3             96  java.lang.StringCoding$StringEncoder107:             2             96  java.lang.ThreadGroup108:             6             96  java.lang.ThreadLocal109:             1             96  java.net.DualStackPlainSocketImpl110:             2             96  java.util.ResourceBundle$BundleReference111:             2             96  java.util.zip.Inflater112:             4             96  jdk.net.ExtendedSocketOptions$ExtSocketOption113:             1             96  sun.misc.Launcher$AppClassLoader114:             3             96  sun.net.spi.DefaultProxySelector$NonProxyInfo115:             2             96  sun.nio.cs.StreamEncoder116:             1             88  sun.misc.Launcher$ExtClassLoader117:             5             80  [Ljava.security.Principal;118:             2             80  java.io.BufferedWriter119:             2             80  java.io.ExpiringCache120:             5             80  java.security.ProtectionDomain$Key121:             2             80  sun.misc.FloatingDecimal$BinaryToASCIIBuffer122:             3             72  java.lang.ThreadLocal$ThreadLocalMap123:             3             72  java.net.Proxy$Type124:             3             72  java.util.Arrays$ArrayList125:             1             72  java.util.ResourceBundle$RBClassLoader126:             3             72  java.util.concurrent.atomic.AtomicLong127:             3             72  sun.misc.FloatingDecimal$ExceptionalBinaryToASCIIBuffer128:             1             72  sun.util.locale.provider.JRELocaleProviderAdapter129:             1             64  [F130:             2             64  [Ljava.lang.Thread;131:             2             64  java.io.FilePermission132:             2             64  java.io.PrintStream133:             2             64  java.lang.ClassValue$Entry134:             2             64  java.lang.StringCoding$StringDecoder135:             2             64  java.lang.VirtualMachineError136:             2             64  java.lang.ref.ReferenceQueue$Null137:             2             64  java.lang.ref.WeakReference138:             2             64  java.security.BasicPermissionCollection139:             2             64  java.security.Permissions140:             2             64  java.util.ResourceBundle$LoaderReference141:             2             48  [Ljava.lang.reflect.Method;142:             2             48  java.io.BufferedOutputStream143:             1             48  java.io.BufferedReader144:             2             48  java.io.File$PathStatus145:             2             48  java.io.FilePermissionCollection146:             2             48  java.io.OutputStreamWriter147:             2             48  java.net.InetAddress$Cache148:             2             48  java.net.InetAddress$Cache$Type149:             1             48  java.net.SocketInputStream150:             1             48  java.nio.HeapCharBuffer151:             2             48  java.nio.charset.CoderResult152:             3             48  java.nio.charset.CodingErrorAction153:             3             48  java.util.Collections$UnmodifiableSet154:             3             48  java.util.HashMap$KeySet155:             2             48  java.util.zip.ZStreamRef156:             2             48  sun.misc.NativeSignalHandler157:             2             48  sun.misc.Signal158:             3             48  sun.net.www.protocol.jar.Handler159:             1             48  sun.nio.cs.StreamDecoder160:             1             48  sun.nio.cs.US_ASCII$Decoder161:             1             48  sun.util.locale.provider.LocaleResources$ResourceReference162:             1             48  sun.util.resources.TimeZoneNames163:             1             48  sun.util.resources.en.TimeZoneNames_en164:             1             40  [Lsun.util.locale.provider.LocaleProviderAdapter$Type;165:             1             40  java.io.BufferedInputStream166:             1             40  java.util.ResourceBundle$1167:             1             40  sun.nio.cs.StandardCharsets$Aliases168:             1             40  sun.nio.cs.StandardCharsets$Cache169:             1             40  sun.nio.cs.StandardCharsets$Classes170:             1             40  sun.nio.cs.ext.ExtendedCharsets171:             1             32  [Ljava.lang.OutOfMemoryError;172:             2             32  [Ljava.lang.StackTraceElement;173:             1             32  [Ljava.lang.ThreadGroup;174:             1             32  [Ljava.net.Proxy$Type;175:             1             32  java.io.WinNTFileSystem176:             1             32  java.lang.ArithmeticException177:             2             32  java.lang.Boolean178:             1             32  java.lang.NullPointerException179:             1             32  java.net.InetAddress$InetAddressHolder180:             1             32  java.net.Socket181:             2             32  java.nio.ByteOrder182:             2             32  java.util.LinkedHashMap$LinkedKeySet183:             2             32  java.util.concurrent.atomic.AtomicInteger184:             1             32  java.util.concurrent.atomic.AtomicReferenceFieldUpdater$AtomicReferenceFieldUpdaterImpl185:             1             32  jdk.net.ExtendedSocketOptions$1186:             1             32  sun.instrument.InstrumentationImpl187:             1             32  sun.nio.cs.StandardCharsets188:             1             32  sun.util.locale.provider.LocaleResources189:             1             32  sun.util.locale.provider.LocaleServiceProviderPool190:             1             24  [Ljava.io.File$PathStatus;191:             1             24  [Ljava.lang.ClassValue$Entry;192:             1             24  [Ljava.net.InetAddress$Cache$Type;193:             1             24  [Ljava.security.ProtectionDomain;194:             1             24  [Lsun.launcher.LauncherHelper;195:             1             24  java.io.InputStreamReader196:             1             24  java.lang.ClassValue$Version197:             1             24  java.lang.StringBuilder198:             1             24  java.lang.invoke.MethodHandleImpl$4199:             1             24  java.lang.reflect.ReflectPermission200:             1             24  java.net.Inet4Address201:             1             24  java.net.Inet6AddressImpl202:             1             24  java.net.Proxy203:             1             24  java.util.BitSet204:             1             24  java.util.Collections$EmptyMap205:             1             24  java.util.Collections$SetFromMap206:             1             24  java.util.Collections$SynchronizedSet207:             1             24  java.util.Locale$Cache208:             1             24  java.util.ResourceBundle$Control$CandidateListCache209:             1             24  java.util.jar.Manifest210:             1             24  sun.instrument.TransformerManager211:             1             24  sun.launcher.LauncherHelper212:             1             24  sun.misc.JarIndex213:             1             24  sun.misc.URLClassPath$FileLoader214:             1             24  sun.nio.cs.ISO_8859_1215:             1             24  sun.nio.cs.ThreadLocalCoders$1216:             1             24  sun.nio.cs.ThreadLocalCoders$2217:             1             24  sun.nio.cs.US_ASCII218:             1             24  sun.nio.cs.UTF_16219:             1             24  sun.nio.cs.UTF_16BE220:             1             24  sun.nio.cs.UTF_16LE221:             1             24  sun.nio.cs.UTF_8222:             1             24  sun.nio.cs.ext.GBK223:             1             24  sun.reflect.NativeMethodAccessorImpl224:             1             24  sun.util.locale.BaseLocale$Cache225:             1             24  sun.util.locale.provider.TimeZoneNameProviderImpl226:             1             16  [Ljava.lang.Throwable;227:             1             16  [Ljava.security.cert.Certificate;228:             1             16  [Lsun.instrument.TransformerManager$TransformerInfo;229:             1             16  java.io.FileDescriptor$1230:             1             16  java.lang.CharacterDataLatin1231:             1             16  java.lang.ClassValue$Identity232:             1             16  java.lang.Runtime233:             1             16  java.lang.String$CaseInsensitiveComparator234:             1             16  java.lang.System$2235:             1             16  java.lang.Terminator$1236:             1             16  java.lang.invoke.MemberName$Factory237:             1             16  java.lang.invoke.MethodHandleImpl$2238:             1             16  java.lang.invoke.MethodHandleImpl$3239:             1             16  java.lang.ref.Reference$1240:             1             16  java.lang.ref.Reference$Lock241:             1             16  java.lang.reflect.ReflectAccess242:             1             16  java.net.InetAddress$2243:             1             16  java.net.URLClassLoader$7244:             1             16  java.nio.Bits$1245:             1             16  java.nio.charset.CoderResult$1246:             1             16  java.nio.charset.CoderResult$2247:             1             16  java.security.ProtectionDomain$2248:             1             16  java.security.ProtectionDomain$JavaSecurityAccessImpl249:             1             16  java.util.Collections$EmptyIterator250:             1             16  java.util.Collections$EmptyList251:             1             16  java.util.Collections$EmptySet252:             1             16  java.util.Hashtable$EntrySet253:             1             16  java.util.ResourceBundle$Control254:             1             16  java.util.WeakHashMap$KeySet255:             1             16  java.util.concurrent.atomic.AtomicBoolean256:             1             16  java.util.jar.Attributes257:             1             16  java.util.jar.JavaUtilJarAccessImpl258:             1             16  java.util.zip.ZipFile$1259:             1             16  jdk.net.ExtendedSocketOptions$PlatformSocketOptions260:             1             16  sun.misc.ASCIICaseInsensitiveComparator261:             1             16  sun.misc.FloatingDecimal$1262:             1             16  sun.misc.Launcher263:             1             16  sun.misc.Launcher$Factory264:             1             16  sun.misc.Perf265:             1             16  sun.misc.Unsafe266:             1             16  sun.net.spi.DefaultProxySelector267:             1             16  sun.net.www.protocol.file.Handler268:             1             16  sun.reflect.DelegatingMethodAccessorImpl269:             1             16  sun.reflect.ReflectionFactory270:             1             16  sun.util.calendar.Gregorian271:             1             16  sun.util.locale.provider.AuxLocaleProviderAdapter$NullProvider272:             1             16  sun.util.locale.provider.SPILocaleProviderAdapter273:             1             16  sun.util.locale.provider.TimeZoneNameUtility$TimeZoneNameGetter274:             1             16  sun.util.resources.LocaleData275:             1             16  sun.util.resources.LocaleData$LocaleDataResourceBundleControl
Total         15169         990792

可以看到最多的对象是String、Class、Object、HashMap。。。

八、性能分析-每秒1000并发的情况下该如何设置jvm的内存?

1、大型购物网站的日常的QPS是多少?
大约是1000QPS
平时购物高峰期,一般集中在2个时间段:11:30—13:30和19:30—21:30
高峰时间段的浏览量PV都是百万级以上,高峰期的QPS约500—1000,我们就按1000来计算。
如果按QPS=1000,1000*3600秒,那一个小时=360万的PV,即每个高峰期2个小时约700万的PV。

2、QPS=1000大概需要多少内存?JVM设置多大?
用户访问一页有10条商品,故每次的response=10条。现在要估算,每条大约多少字节?
假设每件商品最多10个字段(标题、价格、缩略图、原价、点击购物等等),平均每个字段100字节,大约1KB的数据。
那每次访问一页大约是10*1KB=10KB

1000QPS大约需要多少内存?
1000QPS=1000*10KB=10M,也就是说每秒大约需要占用10M的内存数据。

3、QPS=1000多久触发一次ygc?
多久触发一次ygc是由你的堆内存决定的,堆内存够的话时间就长点,堆内存不够的话就短点。
假设我们按1分钟1次触发一次ygc,大约需要配置多少内存?
1s=10m,1min=60*10m=600m
按照young:old=1:2=600:1200,则需要1800M才会1分钟触发1次ygc,所以我们把堆大小设置为2G就能保证分钟级别的GC次数。(如果要2分钟一次ygc,设置为4G)

4、部署多少台机器合适?
按照前面的分析,部署多少台没有太多要求,因为单台已经能支撑1000QPS了。
但为了防止单点故障,提升高可用,一般部署2台。每台承接500QPS。

5、先评估再压测

九、性能分析-系统并发量,突然猛增100倍,该如何解决?
在双十一情况下,浏览量突增

1、从另一个角度思考:我的系统最大并发是多少。即系统每秒最大能处理多少个请求?
(1)单次请求的处理时间=50ms(在互联网公司,所有暴露在公网的接口,都必须低于100ms以下)
(2)那单条线程1s内能处理请求数=1000/50=20次
(3)那有多少条线程呢?
springcloud底层是springboot,springboot底层是tomcat
tomcat底层的线程池,最大的线程数默认是200线程
(4)所以一个微服务,200条线程,每条线程的QPS=20,那整体就是200*20=4000,4000是最大值。
你的服务每秒最大能支撑4000个并发

2、那现在引发另一个问题:能不能优化?能不能再高点?
基本不可能了,一般tomcat200个线程,够大了。
如果50ms是纯CPU计算的,即CPU密集型,CPU只有2核就会出问题的。

什么是CPU密集型?
就是for循环,然后加减乘除的算。
怎么知道CPU密集型?
一般看代码,或者CPU,CPU如果是100%,一般就是。

如果不是纯CPU计算,即IO密集型,问题不大。(什么是IO密集型?就是网络IO或磁盘IO计算)
所以单个服务优化不了,4000并发够可以了

3、4000个并发,jvm运行状况如何?
每次请求约10KB,每秒4000并发=4000*10KB=40MB
年轻代600M / 40M = 15s,即约15s会触发ygc,问题也不大,所以堆设置2G也能支撑4000QPS

4、流量突增100倍并发,如何支撑?
日常请求时1000QPS,突增100倍=10万QPS。
单台理论最大值是4000QPS,10万 / 4000 = 25倍,即25台。
所以我们最起码,要动态新增25台服务来支撑100倍的并发。
如果是CPU密集型计算的,增加的台数绝对大于25台,可能是50台或更高,这个要根据压测来判断。

5、25台机器去那里搞?
答案是:停服务
停其他不重要的服务,例如双11当天,就把不重要的服务停掉,例如退货服务、积分服务、评价服务等等。
事先计划好,一旦大促开始,就把这些不重要的服务停掉。
把服务器腾出来,给例如商品服务这种大促使用,保证大促顺利进行。

Java基础之《JVM性能调优(3)—堆》相关推荐

  1. Netty解决TCP粘包/拆包导致的半包读写问题

    一.TCP粘包/拆包问题说明 TCP是个"流"协议,就是没有界限的一串数据.TCP底层并不了解上层业务数据的具体含义,它会根据TCP缓冲区的实际情况进行包拆分,所以在业务上认为,一 ...

  2. Netty学习总结(5)——Netty之TCP粘包/拆包问题的解决之道

    无论是服务端还是客户端,读取或者发送消息的时候,都需要考虑TCP底层的粘包/拆包机制. TCP粘包/拆包 TCP是个"流"协议. 流:没有界限的一串数据.如同河里的流水,它们是连成 ...

  3. netty解决TCP粘包/拆包导致的半包读写问题的三种方案

    解决方案一:LineBasedFrameDecoder+StringDecoder来解决TCP的粘包/拆包问题 只需要在客户端和服务端加上45.46两行代码并且在发送消息的时候加上换行符即可解决TCP ...

  4. Java基础之《netty(28)—TCP粘包拆包原理》

    一.基本介绍 1.TCP是面向连接的,面向流的,提供高可靠性服务.收发两端(客户端和服务器端)都要有一一成对的socket,因此,发送端为了将多个发给接收端的包,更有效的发给对方,使用了优化方法(Na ...

  5. Netty 之 TCP粘包拆包场景

    转自:http://blog.csdn.net/z69183787/article/details/52595980 TCP编程底层都有粘包和拆包机制,因为我们在C/S这种传输模型下,以TCP协议传输 ...

  6. Netty(二)——TCP粘包/拆包

    转载请注明出处:http://www.cnblogs.com/Joanna-Yan/p/7814644.html 前面讲到:Netty(一)--Netty入门程序 主要内容: TCP粘包/拆包的基础知 ...

  7. java tcp怎么拆包_Java网络编程基础之TCP粘包拆包

    TCP是个"流"协议,所谓流,就是没有界限的一串数据.大家可以想象河里的流水,他们是连成一片的,其间并没有分界线.TCP底层并不了解上层业务数据的具体含义,他会根据TCP缓冲区的实 ...

  8. 《精通并发与Netty》学习笔记(13 - 解决TCP粘包拆包(一)概念及实例演示)

    一.粘包/拆包概念 TCP是一个"流"协议,所谓流,就是没有界限的一长串二进制数据.TCP作为传输层协议并不不了解上层业务数据的具体含义,它会根据TCP缓冲区的实际情况进行数据包的 ...

  9. Netty详解(五):Netty TCP粘包 拆包

    1. 概述 无论是服务端还是客户端,我们读取或者发送消息的时候,都需要考虑TCP底层的粘包和拆包机制.下面我们来通过Netty来详解TCP底层的粘包和拆包机制. 2. TCP底层的粘包和拆包机制 TC ...

  10. 一起学Netty(六)之 TCP粘包拆包场景

    TCP编程底层都有粘包和拆包机制,因为我们在C/S这种传输模型下,以TCP协议传输的时候,在网络中的byte其实就像是河水,TCP就像一个搬运工,将这流水从一端转送到另一端,这时又分两种情况: 1)如 ...

最新文章

  1. vector相关习题
  2. 【重复制造精讲】1、入门介绍
  3. Hard Calculation 模拟(200)
  4. java自定义返回码_java – 自定义HTTP状态代码
  5. 刪數 (Standard IO)
  6. java transaction cn_GitHub - cnzebra/tcc-transaction: tcc-transaction是TCC型事务java实现
  7. jQuery使用CDN加速
  8. 18000 6c java_面向ISO18000-6C协议的无源超高频射频识别标签芯片设计
  9. 在c语言中数组下标的最小值,数组元素下标的上限_c语言中,数组元素的下标下限为...
  10. 问题:连接查询和子查询的区别和连接及优劣?
  11. postgresql安装过程小记
  12. .NET图像处理包 DotImage
  13. WEB前端--Day9(动画)
  14. python中base函数_详细的python basemap中各函数的所有参量注释
  15. 西藏计算机一级,西藏计算机等级考试级别
  16. C++:高斯坐标,大地坐标转经纬度
  17. 「实时视频流分析的边缘计算技术」最新2022研究综述
  18. python云盘私有云_GitHub - 0x2642/Umi-Chest: 一个基于python的私有云实验项目
  19. 文字检测与识别1-MSER
  20. mysql 单表关联_MySQL 基础之 单表、多表联查

热门文章

  1. custom_dataset
  2. husky v8 lint-stage eslint
  3. 八数码 BFS+HASH
  4. 厦门理工学院oj 1107-牲口棚的安全
  5. ios 绘制线框_16款值得一用的iPhone线框图模板 (PSD Sketch)
  6. java pnpoly算法_PNPoly算法代码例子,判断一个点是否在多边形里面
  7. 信息安全的江湖 只有圈内人玩的转
  8. 平方预测误差(Squared prediction error,SPE)和霍特林统计量(Hotelling’s T2)原理
  9. Windows系统中设置软件的开机自动启动
  10. “解决Python软件包安装问题 - 修改pip源地址“