首页 > 编程语言 >java部分底层原理了解

java部分底层原理了解

时间:2023-03-06 22:05:06浏览次数:33  
标签:arr java int 内存 new 原理 底层 方法 sout

Java内存分配

其中在JVM虚拟机中

jvm的内存分为五个部分:

这个只是在JDK之前的JVM内存图

在JDK8开始:取消了方法区,增加了元空间,把原来的方法区的多种功能进行拆分,有的功能放在了堆空间中,有的放在了元空间

  • 栈:方法运行时使用的内存,比如main方法运行,进入方法栈中执行

    方法开始执行会进栈,执行完毕会出栈(栈是一种数据结构,具体去学数据结构)

  • 堆:存储对象或数组,new创建的东西都存在堆内存中

    new出来的东西都会在这个内存中开辟空间并且产生地址值

  • 方法区:存储可以运行的class文件(jdk8开始将方法区拆解了,新增元空间,并且元空间存储可以运行的class文件)

  • 本地方法栈:JVM在使用操作系统功能的时候使用,不需要了解

  • 寄存器:给CPU使用,不需要了解

数组的内存图

举例:

public static void main(String[] args){
    int[] arr=new int[2];
    sout(arr);
    sout(arr[0]);
    sout(arr[1]);
    
    arr[0]=11;
    arr[1]=22;
    sout(arr[0]);
    sout(arr[1]);
    
    int[] arr2={33,44,55};
    sout(arr2);
    sout(arr1[0]);
    sout(arr2[1]);
    sout(arr2[2]);
}

上述代码执行流程:

  1. main方法压入栈内存中

  2. 执行int[] arr=new int[2];

    具体执行:

    ​ 在堆内存中创建数组空间并产生地址值

    ​ 把这个地址值赋值给arr

  3. 执行代码sout(arr)此时是打印出了arr的地址值

  4. 执行代码sout(arr[0])通过arr找到数组在堆内存中的地址,通过[0]找到对应地址中对应的数据

  5. sout(arr[1])同理

  6. arr[0]=11;如果arr[0]找到堆内存中开辟的空间中的对应数值存放地点,并且给他赋值11

  7. arr[1]=22同理

  8. 执行代码int[] arr2={33,44,55};虽然没有new但是实质还是在堆空间中创建内存

    这俩个内存之间互不干扰

  9. 具体如下

注:如果是这种情况

public static void main(String[] args){
    int[] arr=new int[2];
    int[] arr2=arr;
    //这个代表的是把arr的地址值赋值给arr2
    //此时修改arr的内容同时arr2也会改变!因为arr2存储的只是地址值!!!
}

方法的内存图

方法调用的内存原理

public class Test{
	public static void main(String[] args){
        eat();
	}
    public static void eat(){
        study();
        sout("吃饭");
        sleep();
    }
    public static void sleep(){
        sout("睡觉");
    }
    public static void study(){
        sout("学习");
	}
}

方法被调用后就会进栈运行

当方法执行完毕后,方法会出栈,此时栈内开辟的变量也随着销毁

上面代码执行后如图

当所有方法进栈之后,就会开始执行了,执行完毕后会一个个出栈

对象内存图

  • 一个对象的内存图

    Student s=new Student();

    1. 加载class文件
    2. 声明局部变量
    3. 在堆内存中开辟一个空间
    4. 默认初始化or显示初始化(如果在类中给变量赋值了就加载显示初始化,否则加载默认初始化)
    5. 构造方法初始化
    6. 将堆内存中的地址值赋值给左边的变量

当main方法也出栈的时候,此时没东西指向堆内存。故会自动销毁

类中的方法是先在方法区中加载,然后随着顺序执行的时候。

调用该方法才进栈

  • 两个对象的内存图

和一个对象的内存图区别就是,方法区只需要加载一次!堆内存new几次开辟几次

  • 两个引用指向同一个对象

this的内存原理

thi作用:区分局部变量和成员变量

this本质:所在方法调用者的地址值

字符串相关底层原理

  • 字符串存储的内存原理

    1. 直接赋值会复用字符串常量池中的字符串

      串池中有才会复用,没有则会在串池中新建对应的字符串

    2. new出来的不会复用,而是在堆内存中开辟一个新空间

  • ==号比较的到底是什么

    1. 基本数据类型比较的是数据值
    2. 引用数据类型比较的是地址值

    一般用equals方法来比较而不是==

  • 字符串拼接的底层原理

    1. 等号右边没有变量

    2. 等号右边有变量

      • 在jdk8之前

      • 在jdk8之后

        jvm会先预估字符串的长度,然后创建数组字符串,然后把数组变成字符串

      综上!字符串不建议直接用+这样即使底层有优化但是还是很慢非常影响效率!一般用StringBuilder进行拼接

  • StringBuilder源码分析

  1. 默认创建一个长度为16的字节数组
  2. 添加内容长度小于16直接保存
  3. 添加内容大于16扩容!(原容量*2+2)
  4. 如果还是不够就以实际为准

标签:arr,java,int,内存,new,原理,底层,方法,sout
From: https://www.cnblogs.com/wdadwa/p/17182088.html

相关文章

  • java8 分组排序
    //先根据姓名分组再根据分数排序Map<String,List<Student>>map1=listAll.stream().collect(Collectors.groupingBy(Student::getName,HashMap::new,Colle......
  • Java 变量一定要初始化吗?
    1.问题Java中,变量一定要初始化吗?2.解答不一定。a.变量作为局部变量变量作为局部变量时,如果不对其赋值,又要使用它,那就必须得初始化,否则报错。publicclass......
  • Java实验-Swing 网络聊天室
    实验要求:综合Swing界面、多线程和Java的网络通信功能,实现仿QQ聊天:(1)界面设计如下:(2)要求在服务器端利用多线程响应客户端请求;//服务线程(内部类),用于处理客户端的服务线......
  • 计算机组成原理--性能指标
             ......
  • 一次Java服务内存过高的分析过程
    现象年前,收到了短信报警,显示A服务的某台机器内存过高,超过80%如上图所示,内存会阶段性增加。奇怪的是,十多台机器中只有这一台有这个问题堆内内存分析最先怀疑是内存泄漏......
  • 解决 IntelliJ IDEA 2019.2.3 java 工程运行中文乱码问题
    前言java语言的语法类似于C++,目前接触的开发环境:eclipse与IntelliJIDEA,AndroidStudio应该跟IntelliJIDEA很类似虽然之前改改AndroidAPK,了解了一些java开发相关的东......
  • Java应用【XV】使用Java中的TensorFlow来构建和训练机器学习模型
    如果您觉得本博客的内容对您有所帮助或启发,请关注我的博客,以便第一时间获取最新技术文章和教程。同时,也欢迎您在评论区留言,分享想法和建议。谢谢支持!一、引言1.1TensorFlow......
  • Java知识脉络图
    吾心安处即吾乡。吾乡何处不可眠1.Java基础全程脉络图2.本章专题与脉络......
  • Java开发环境安装JDK以及概念
    1、JDK、JRE、JVM概念JDK:JavaDevelopmentKit(Java开发者工具)JRE:JavaRuntimeEnvironment(Java运行时环境)JVM:JavaVirtualMachine(Java虚拟机)JDK(Java开发者工具)......
  • JavaScript对象及面向对象基础(对象、构造函数、原型对象、继承、原型链、借用构造函数
    JavaScript是一种描述性语言,是一种基于对象和事件驱动的,具有安全性能的脚本语言。JavaScript语言是通过一种叫做“原型”的方式来实现面向对象编程的。一、对象(1)内置对象Str......