关于JAVA程序的内存分布

news2024/12/26 22:11:06

目录

1.Java程序运行时内存说明

2.JVM内存划分

3.Java中数据类型

4.Java中的String

5.结合HelloWorld分析java程序内存分布


1.Java程序运行时内存说明

          编写的.java程序文件需要java编译器javac转成.class文件,然后通过jvm(名为java的可执行程序)来加载.class文件执行。每运行一个java程序就会产生一个java(JVM)的实例。一个java进程对应一个JVM实例,该进程可能包含一个或者多个线程,每个JVM实例都有一个对应的堆,每个线程有自己私有的栈。进程创建的所有类的对应本身何数组本身存放在堆上,由进程所有的线程共享。Java中堆上为对象分配内存会初始化这个对象中的变量。堆上对象的引用是再栈中分配,创建一个对象再堆和栈上都分配内存,堆中分配的内存存放对象本身,而在栈中分配的内存呢只是存放指向这个堆对象的引用而已。在函数栈帧中new出来一个局部变量时,在栈空间和堆空间中分配空间,当局部变量生命周期结束后,栈空间立刻被回收,堆空间区域等待GC回收。

2.JVM内存划分

JVM的内存可分为3个区:堆(heap)、栈(stack)和方法区(method,也叫静态区):

堆区: 
(1)存储的全部是对象,每个对象都包含一个与之对应的class的信息(class的目的是得到操作指令) ;
(2)jvm只有一个堆区(heap),且被所有线程共享,堆中不存放基本类型和对象引用,只存放对象本身和数组本身;

栈区: 
(1)每个线程包含一个栈区,栈中只保存基础数据类型本身和自定义对象的引用;
(2)每个栈中的数据(原始类型和对象引用)都是私有的,其他栈不能访问;
(3)栈分为3个部分:基本类型变量区、执行环境上下文、操作指令区(存放操作指令);

方法区(静态区): 
(1)被所有的线程共享,方法区包含所有的class(class是指类的原始代码,要创建一个类的对象,首先要把该类的代码加载到方法区中,并且初始化)和static变量。 
(2)方法区中包含的都是在整个程序中永远唯一的元素,如class,static变量。 
堆(heap)和栈(stack)的区别 :
(1)栈(stack)与堆(heap)都是Java用来存放数据的地方。与C++不同,Java自动管理栈和堆,程序员不能直接地设置栈或堆。 
(2)栈的优势是,存取速度比堆要快,仅次于直接位于CPU中的寄存器。但缺点是,存在栈中的数据大小与生存期必须是确定的,缺乏灵活性。
堆的优势是可以动态地分配内存大小,生存期也不必事先告诉编译器,Java的垃圾收集器会自动收走这些不再使用的数据。
但缺点是由于要在运行时动态分配内存,存取速度较慢。

3.Java中数据类型

(1)基本类型(primitive types), 共有8类,即int, short, long, byte, float, double, boolean, char。
这种类型的定义是通过诸如int a = 3; long b = 255L;的形式来定义的,称为自动变量。自动变量存的是字面值,不是类的实例,
即不是类的引用,这里并没有类的存在。如int a = 3; 这里的a是一个指向int类型的引用,指向3这个字面值。
这些字面值的数据,由于大小可知和生存期可知(这些字面值固定定义在某个程序块里面,程序块退出后,字段值就消失了),出于追求速度的原因,就存在于栈中。 
(2)包装类数据,如Integer, String, Double等将相应的基本数据类型包装起来的类。
这些类数据全部存在于堆中,Java用new()语句来显示地告诉编译器,在运行时才根据需要动态创建,因此比较灵活,但缺点是要占用更多的时间。 
(3)自定义数据类型
用new()语句创建,对象存放在在堆区,通过栈区的引用来使用。

4.Java中的String

(1)栈的共享特性
String str1 = "abc";
String str2 = "abc";
System.out.println(str1==str2); //true
说明:
1)编译器先处理String str1 = "abc";它会在栈中创建一个变量为str1的引用,然后查找栈中是否有abc这个值,如果没找到,就将abc存放进来,然后将str1指向abc。
2)接着处理String str2 = "abc";在创建完b的引用变量后,因为在栈中已经有abc这个值,便将str2直接指向abc。这样,就出现了str1与str2同时均指向abc的情况。
所以我们在使用诸如String str = "abc";的格式定义类时,总是想当然地认为,创建了String类的对象str。其实对象可能并没有被创建(在栈上创建),而可能只是指向一个先前已经创建的对象。
(2)堆内存
通过new()方法才能保证每次都创建一个新的对象。其存放在堆上。由于String类的immutable性质,当String变量需要经常变换其值时,应该考虑使用StringBuffer类,
以提高程序效率。

5.结合HelloWorld分析java程序内存分布

HelloWorld.java

//import java.lang.Integer;

public class HelloWorld {  //运行时jvm 把HelloWorld的代码全部都放入方法区     
    public static void main(String[] args) {  //main方法放在方法区
        System.out.println("Hello World!");
		Student stu = new Student(110, "Andy", 18);  //stu在栈上,引用堆上new出来的对象,new Student(110, "Andy", 18)在堆上存储
		stu.printStudent();
		int[] iArr = new int[10]; //iArr在栈上,引用堆上new出来的对象,new int[10]在堆上存储
		for (int i = 0; i < 10; i++) {
			iArr[i] = i;
		}
		System.out.println("iArr: " + iArr);
		int[] iArr1 = {12, 34, 45, 60, 45, 82};
		System.out.println("iArr: " + iArr1);
    }
}

class Student { //运行时jvm 把Student的代码全部都放入方法区   
private int id;
private String name;
private Integer age;   
    
public Student(int id, String name, Integer age) {     
	this.id = id;
	this.name = name;
	this.age = age;
}     
   
   
public void  printStudent() { //printStudent方法放在方法区
	System.out.println("id: " + id); 
	System.out.println("name: " + name); 
	System.out.println("age: " + age); 
}  
   
}

编译运行:

 备注:错误 【错误: 编码GBK的不可映射字符】解决办法

报错原因:windows下默认的字符集为:GBK,而当你的java文件当中的汉字不是字符集:GBK时,javac进行编译的时候就会报错。

解决方法:

(1)javac指定文件编码方式,例如

javac -encoding UTF-8 HelloWorld.java

(2)将文件编码设置成GBK编码

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/932466.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

智慧能源助力绿色发展

居民生活是碳排放的重要贡献源&#xff0c;作为居民生活的主要场所&#xff0c;社区是低碳城市建设的重要空间载体。推动低碳社区建设&#xff0c;逐渐打造低碳生活方式&#xff0c;是低碳社会建设的重要内容之一。智慧新能源公共设施助力碳中和&#xff0c;用于各社区改造&…

【RuoYi移动端】uni-app如何发布h5网站?

一、登录D-Cloud开发者中心 开发者中心https://dev.dcloud.net.cn/二、创建应用 三、填写和提交创建应用 四、复制APPID

strcmp 的使用和模拟

目录 函数介绍&#xff1a; 头文件&#xff1a; 语法&#xff1a; 代码演示&#xff1a; 函数模拟&#xff1a; 函数介绍&#xff1a; strcmp是比较大小的函数。从字符串开始进行比较&#xff0c;如果两个相同位置的字符相同&#xff0c;那么继续往下进行比较&#xff0c;…

最大子数组和【贪心算法】

最大子数组和 给你一个整数数组 nums &#xff0c;请你找出一个具有最大和的连续子数组&#xff08;子数组最少包含一个元素&#xff09;&#xff0c;返回其最大和。 子数组 是数组中的一个连续部分。 class Solution {public int maxSubArray(int[] nums) {//记录最大结果&…

数据结构—循环队列(环形队列)

循环队列&#xff08;环形队列&#xff09; 循环队列的概念及结构循环队列的实现 循环队列的概念及结构 循环队列是一种线性数据结构&#xff0c;其操作表现基于 FIFO&#xff08;先进先出&#xff09;原则并且队尾被连接在队首之后以形成一个循环。它也被称为“环形缓冲器”。…

W25Q64 驱动--基于SPI2接口

前言 &#xff08;1&#xff09;本系列是基于STM32的项目笔记&#xff0c;内容涵盖了STM32各种外设的使用&#xff0c;由浅入深。 &#xff08;2&#xff09;小编使用的单片机是STM32F105RCT6&#xff0c;项目笔记基于小编的实际项目&#xff0c;但是博客中的内容适用于各种单片…

使用Miniconda

Conda是一个开源的包和环境管理器&#xff0c;使用它可以在同一台机器上安装不同版本的Python软件包和依赖了。Anaconda和Miniconda都集成了Conda,Anaconda包括更多的工具包&#xff0c;Miniconda则只包括Conda和Python。 在很奇葩的Deepin下Miniconda安装之旅 中&#xff0c;…

React + Next.js 搭建项目(配有对比介绍一起食用)

文章标题 01 Next.js 是什么02 Next.js 搭建工具 create-next-app03 create-react-app 与 create-next-app 的区别04 快速构建 Next.js 项目05 App Router 与 Pages Router 的区别 01 Next.js 是什么 Next.js 是一个 React 框架&#xff0c;它允许你使用 React 框架建立超强的…

sin(A)的意义

若存在矩阵A&#xff0c;则sin(A)表示对于矩阵A的每一个元素&#xff0c;进行对应的函数运算。 如:

LabVIEW软件安装包分享(附安装教程)

目录 一、软件简介 二、软件下载 一、软件简介 LabVIEW&#xff08;Laboratory Virtual Instrument Engineering Workbench&#xff09;是由美国National Instruments&#xff08;简称NI&#xff09;公司开发的一款图形化编程工具&#xff0c;广泛应用于测试、测量和控制系统…

微信开放注册微信小号功能,工作人群福音!

微信&#xff0c;这个坐拥数亿用户的社交巨头&#xff0c;最近终于开放了注册微信小号的功能。这个功能对于需要多个微信账号进行工作的人来说&#xff0c;无疑是一场及时雨&#xff0c;极大地提高了工作便利性。 在之前的版本中&#xff0c;每个微信账号都绑定了一个手机号&am…

Docker架构及原理

一、Docker的架构图 二、底层原理 Docker是怎么工作的&#xff1f; Docker是一个Client-Server结构的系统&#xff0c;Docker守护进程运行在主机上&#xff0c; 然后通过Socket连接从客户端访问&#xff0c;守护进程从客户端接受命令并管理运行在主机上的容器。 容器&#xf…

【C++心愿便利店】No.3---内联函数、auto、范围for、nullptr

文章目录 前言&#x1f31f;一、内联函数&#x1f30f;1.1.面试题&#x1f30f;1.2.内联函数概念&#x1f30f;1.3.内联函数特性 &#x1f31f;二、auto关键字&#x1f30f;2.1.类型别名思考&#x1f30f;2.2.auto简介&#x1f30f;2.3.auto的使用细节&#x1f30f;2.4.auto不能…

【java】【项目实战】[外卖五]菜品管理业务开发

目录 一、文件上传与下载 1.1 文件上传介绍 1.2 文件下载介绍 1.3 文件上传代码实现 1.3.1 新增upload.html 1.3.2 修改application.yml 1.3.3 CommonController 1.3.4 功能测试 1.4 文件下载代码实现 1.4.1 CommonController 1.4.2 功能测试 二、新增菜品 2.1 需…

VSCode下载安装使用

天行健&#xff0c;君子以自强不息&#xff1b;地势坤&#xff0c;君子以厚德载物。 每个人都有惰性&#xff0c;但不断学习是好好生活的根本&#xff0c;共勉&#xff01; 文章均为学习整理笔记&#xff0c;分享记录为主&#xff0c;如有错误请指正&#xff0c;共同学习进步。…

HTTPS协议加密原理

目录 一、什么是HTTPS 二、什么是加密/解密 三、为什么要加密 四、常见的加密方式 1.对称加密 2. 非对称加密 五、HTTPS加密方式探讨 1.只使用对称加密 2.只使用非对称加密 3.非对称加密对称加密 4.非对称加密对称加密CA认证 六、总结 一、什么是HTTPS HTTP 协议&a…

BGP路由协议的那些事?(下)

BGP路由协议的那些事?(下) 上期问题:在BGP联盟内部的EBGP和IBGP对等体互相传递路由时,LP属性和MED属性是如何变化的呢? 还记得我们说BGP联盟的规则时,有两条关于LP属性和MED属性的规则怎么说来着: 1:路由的LOCAL_PREF属性在整个联盟中都被保留,而不仅仅是在为它们…

Fooocus-开源AI绘画工具 无需繁琐配置 一键下载安装

工具介绍 Fooocus是一款免费开源的AI绘画工具&#xff0c;基于SDXL模型在SD webui的基础上进行了改进&#xff0c;提供了一系列强大功能&#xff0c;并提供直观易懂的界面&#xff0c;离线、开源、免费&#xff0c;无需手动调整参数等等&#xff0c;一键下载安装&#xff0c;用…

什么是回调函数(callback function)?

聚沙成塔每天进步一点点 ⭐ 专栏简介⭐ 回调函数&#xff08;Callback Function&#xff09;⭐ 示例⭐ 写在最后 ⭐ 专栏简介 前端入门之旅&#xff1a;探索Web开发的奇妙世界 记得点击上方或者右侧链接订阅本专栏哦 几何带你启航前端之旅 欢迎来到前端入门之旅&#xff01;这…

ZDH-智能营销模块

本次介绍基于ZDH v5.1.2版本 项目源码 zdh_web: GitHub - zhaoyachao/zdh_web: 大数据采集,抽取平台 营销模块后端服务: 开发中 预览地址 后台管理-登陆 用户名&#xff1a;zyc 密码&#xff1a;123456 安装包下载地址 登录预览系统-可下载安装包 重要提示 当前模块支持的…