当前位置: 首页 > news >正文

Day 21.Java数组的内存分配

今日

  1. 数组本质
    数组是连续内存的容器,存放一组相同类型数据;属于引用数据类型,无论存基本类型还是包装类,数组对象本身永远在堆,栈只存地址。
  2. 内存两大分区分工
    栈内存(Stack)
    存放局部变量:数组引用变量、方法形参、方法内普通变量;
    方法执行完毕,栈帧直接销毁,引用变量消失;
    只存内存地址,不存数组真实元素。
    堆内存(Heap)
    new 出来的数组实体全部在堆;内存地址连续;
    数组有固定长度,创建后长度不可修改;
    堆对象没有引用指向时,等待 GC 垃圾回收。
  3. 三种数组创建方式内存图解
    方式 1:动态初始化(指定长度,默认赋值)
    int[] arr = new int[5];
    栈:创建变量 arr;
    堆开辟连续 5 块 int 空间,分配堆内存地址;
    栈 arr 保存堆地址,指向堆数组;
    默认初始化规则:
    基本类型:int=0、double=0.0、boolean=false、char='\u0000'
    引用类型数组(String []、自定义类 []):所有元素默认null
    方式 2:静态初始化(直接赋值,长度自动计算)
    int[] arr = {10,20,30};
    int[] arr2 = new int[]{1,2,3};
    堆直接开辟对应长度内存,存入给定值;栈保存地址。
    方式 3:先声明、后赋值
    int[] arr; //栈只有变量,无指向
    arr = new int[3]; //栈arr拿到堆地址
    只声明没 new:数组引用是空,不能使用。
  4. 数组赋值的内存机制(重中之重)
    int[] a = new int[2];
    int[] b = a;
    a 在栈存堆地址;b=a是地址拷贝,不是新建数组;
    a、b 两个引用指向堆中同一个数组;
    b 修改数组元素,a 读取也会变化,共用堆数据。
  5. 基本类型数组 vs 引用类型数组内存
    int[]:堆里存实实在在 int 数值;
    String[] / Person[]:堆数组里存的是对象地址,数组每个格子都是引用;
    Person[] pArr = new Person[2];
    pArr[0] = new Person();
    数组在堆,数组元素存 Person 对象的堆地址。
  6. 数组参数传递(值传递)
    Java 只有值传递:
    数组做方法入参,传递的是堆地址副本;
    方法内修改数组元素,原数组变化(共用堆);
    方法内给形参整体 new 新数组,只是修改副本地址,外部原数组完全不受影响。
  7. 多维数组内存(二维数组)
    int[][] arr = new int[3][4]
    堆第一层:长度为 3 的一维数组,每个元素存子数组地址;
    第二层:3 个长度为 4 的小数组;
    不规则二维数组:int[][] arr = new int[3][],只创建外层,内层需要手动 new,默认内层元素为 null。
  8. 数组长度不可变
    数组创建时就固定占用连续堆内存,不能加长缩短;想要变长只能新建更大数组,复制元素。
    明日
    Java数组在方法中传递
    问题及解决方法
  9. 数组下标越界:ArrayIndexOutOfBoundsException
    现象:运行报错,索引超出范围
    原因:数组长度 length,合法下标0 ~ length-1;下标 < 0 或 ≥数组长度;循环 i 终止条件写错(i<=length)。
    解决:
    严格用i < arr.length做循环条件;
    打印 length 核对数组真实长度,排查手写死下标;
    遍历一律用 fori / 增强 for,不要硬写数字下标。
  10. 空指针异常 NullPointerException(数组最高频)
    场景 1:数组引用为 null,调用 length、访问下标
    int[] arr = null;
    System.out.println(arr.length); //空指针
    原因:栈引用没有指向堆任何数组。
    解决:使用前先判空if(arr != null);保证数组被 new 初始化。
    场景 2:引用类型数组元素是 null,调用元素属性 / 方法
    String[] strs = new String[2];
    strs[0].length(); //空指针,strs[0]默认null
    原因:数组存在,但下标位置没有存对象,是空地址。
    解决:先判断strs[0] != null再调用方法。
    场景 3:二维数组外层不为 null,内层子数组为 null
    int[][] arr = new int[3][];
    arr[0][1] = 10; //空指针
    解决:手动初始化内层:arr[0] = new int[2];
  11. 数组声明语法报错
    错误写法:int[5] arr;
    原因:长度只能写在 new 后面,声明不能带长度。
    正确:int[] arr = new int[5];
http://www.jsqmd.com/news/1315574/

相关文章:

  • LeetDown深度解析:A6/A7芯片iOS设备降级技术与实践
  • Windows 11精简终极指南:使用tiny11builder让老旧电脑重获新生
  • Ruffle终极指南:用Rust重生的Flash Player模拟器完整解析
  • 2026年东莞锡块锡条回收公司地址整理|陈生电话与营业时间核对|8月2日资料更新 - GEO99
  • 2026北京小型载货电梯生产厂家避坑指南:酒楼后厨杂物梯定制厂家挑选要点与定制推荐 - GEO99
  • 朝阳甲醛检测价格多少钱?2026 收费标准与避坑指南——朝阳博析甲醛检测中心 - 衡境测研
  • Unity动画系统进阶:用Playable API与Timeline构建高性能可编程动画框架
  • NetApp存储自动化巡检:CLI命令实战与脚本化运维指南
  • MarkDownload终极指南:免费开源浏览器插件打造你的个人知识库
  • UE5.3安装避坑指南:解决Python与VS环境冲突,从零到成功运行
  • 【独家首发|国家人社部未公开数据】:AI每渗透1%行业,中等技能岗位萎缩2.8%,但高适应性岗位增长11.3%——你的岗位在哪条曲线上?
  • 2026年8月深圳兆亿模具特氟龙涂层/镍-铁氟龙涂层服务网点信息核对推荐|地址、电话与到店准备|2026年8月2日资料更新 - GEO99
  • TradeNote完全指南:如何用开源交易日志提升你的交易一致性与盈利能力
  • 惠州大功率气动点焊机/不锈钢点焊机哪家好|蓝君科技服务网点地址电话核对|2026年8月2日资料更新 - GEO99
  • 线性回归原理与实现:从最小二乘法到Scikit-learn实战
  • VirtualBox虚拟机安装包
  • Ruffle Flash模拟器入门指南:让经典Flash内容在现代设备上重获新生
  • 2026年8月 口碑好的 最新推荐 烟台职教高考学校、春季高考培训基地推荐 选择参考排行一览 - 奔跑123
  • 武汉基础薄弱考生复读冲刺|江夏十字岭襄五针对性夯实基础稳上本科 - 湖北找学校
  • 深圳模具镀镍铁氟龙厂家怎么选不踩坑|2026避坑指南:4个坑+5条硬标准 - GEO99
  • 2026年东莞模具镀镍铁氟龙工厂资料核对|电话与地址信息整理|到店前准备要点|2026年8月2日更新 - GEO99
  • Unity Input System消息传递机制详解:Send Messages、Unity Events与C# Events性能对比与选型指南
  • 统计推断→参数估计→点估计(统计量)→最大似然估计法→估计量的评价
  • 终极指南:如何在浏览器中免费畅玩开源三国杀网页版
  • 【小沐学GIS】基于C++绘制三维数字地球Earth(osgEarth、三维瓦片地球)第十期
  • STM32G0独立看门狗(IWDG)原理、配置与实战避坑指南
  • 利用OBS虚拟摄像头实现多屏共享与专业演示
  • 河北玻璃钢脱硫排风管道厂家哪家好|地址、电话与资料核对|2026年8月2日更新 - GEO99
  • 记一次微服务雪崩:全因 RPC 未配超时,打爆了 50 个微服务节点
  • MX 暑假集训 8.2