精华内容
下载资源
问答
  • 数组在内存中的存储方式

    千次阅读 2020-07-21 11:07:59
    数组是一种引用数据类型,数组引用变量只是一...下面将深入介绍数组在内存中的运行机制。 数组引用变量只是一个引用,这个引用变量可以指向任何有效的内存,只有当该引用指向有效内存后,才可通过该数组变量来访问数...

    数组是一种引用数据类型,数组引用变量只是一个引用,数组元素和数组变量在内存里是分开存放的。下面将深入介绍数组在内存中的运行机制。

    数组引用变量只是一个引用,这个引用变量可以指向任何有效的内存,只有当该引用指向有效内存后,才可通过该数组变量来访问数组元素。

    与所有引用变量相同的是,引用变量是访问真实对象的根本方式。也就是说,如果我们希望在程序中访问数组,则只能通过这个数组的引用变量来访问它。

    实际的数组元素被存储在堆(heap)内存中;数组引用变量是一个引用类型的变量,被存储在栈(stack)内存中。数组在内存中的存储示意图如图4.2所示:
    图4.2 数组在内存中的存储示意图
    如果需要访问图4.2中堆内存中的数组元素,程序中只能通过p[index]的形式实现。也就是说,数组引用变量是访问堆内存中数组元素的唯一方式。

    为什么有栈内存和堆内存之分?

    当一个方法执行时,每个方法都会建立自己的内存栈,在这个方法内定义的变量将会逐个放入这块栈内存里,随着方法的执行结束,这个方法的内存栈也将自然销毁了。因此,所有在方法中定义的变量都是放在栈内存中的;当我们在程序中创建一个对象时,这个对象将被保存到运行时数据区中,以便反复利用(因为对象的创建成本通常较大),这个运行时数据区就是堆内存。堆内存中的对象不会随方法的结束而销毁,即使方法结束后,这个对象还可能被另一个引用变量所引用(方法的参数传递时很常见),则这个对象依然不会被销毁。只有当一个对象没有任何引用变量引用它时,系统的垃圾回收机制才会在合适的时候回收它。

    如果堆内存中数组不再有任何引用变量指向自己,则这个数组将成为垃圾,该数组所占的内存将会被系统的垃圾回收机制回收。因此,为了让垃圾回收机制回收一个数组所占的内存空间,则可以将该数组变量赋为null,也就切断了数组引用变量和实际数组之间的引用关系,实际数组也就成了垃圾。

    只要类型相互兼容,可以让一个数组变量指向另一个实际的数组,这种操作会产生数组的长度可变的错觉。如下代码所示:

    程序清单:codes/04/4-6/ArrayInRam.java
    public class ArrayInRam
    {
    public static void main(String[] args) 
    {
    //定义并初始化数组,使用静态初始化
    int[] a = {5, 7 , 20};
    //定义并初始化数组,使用动态初始化
    int[] b = new int[4];
    //输出b数组的长度
    System.out.println("b数组的长度为:" + b.length);
    //循环输出a数组的元素
    for (int i = 0 ; i < a.length ; i++ )
    {
    System.out.println(a[i]);
    }
    //循环输出b数组的元素
    for (int i = 0 ; i < b.length ; i++ )
    {
    System.out.println(b[i]);
    }
    //因为a是int[]类型,b也是int[]类型,所以可以将a的值赋给b。
    //也就是让b引用指向a引用指向的数组
    b = a;
    //再次输出b数组的长度
    System.out.println("b数组的长度为:" + b.length);
    }
    }
    • 1
    • 2
    • 3
    • 4
    • 5
    • 6
    • 7
    • 8
    • 9
    • 10
    • 11
    • 12
    • 13
    • 14
    • 15
    • 16
    • 17
    • 18
    • 19
    • 20
    • 21
    • 22
    • 23
    • 24
    • 25
    • 26
    • 27
    • 28

    运行上面代码后,将可以看到先输出b数组的长度为4,然后依次输出a数组和b数组的每个数组元素,接着会输出b数组的长度为3。看起来似乎数组的长度是可变的,但这只是一个假象。必须牢记:定义并初始化一个数组后,在内存里分配了两个空间,一个用于存放数组的引用变量,一个用于存放数组本身。下面将结合示意图来说明上面程序的运行过程。

    当程序定义并初始化了a、b两个数组后,系统内存中实际上产生了4块内存区,其中栈内存中有两个引用变量:a和b;堆内存中也有两块内存区,分别用于存储a和b引用所指向的数组本身。此时计算机内存的存储示意如图4.3所示:

    图4.3 定义并初始化a、b两个数组

    从图4.3中可以非常清楚地看出,a引用和b引用所指向数组里数组元素的值,并可以很明白地看出b数组的长度是4。

    当执行上面粗体字标识代码:b = a代码时,系统将会把a的值赋给b,a和b都是引用类型变量,存储的是地址。因此把a的值赋给b后,就是让b指向a所指向的地址。此时计算机内存的存储示意如图4.4所示:

    图4.4 让b引用指向a引用所指向数组

    从图4.4中可以看出,当执行了b = a之后,堆内存中第一个数组具有了两个引用:a变量和b变量都指向了第一个数组。此时第二个数组失去了引用,变成垃圾,只有等待垃圾回收来回收它——但它的长度依然不会改变,直到它彻底消失。

    程序员进行程序开发时,不要仅仅停留在代码表面,而要深入底层的运行机制,才可以对程序的运行机制有更准确的把握。当我们看一个数组时,一样要把数组看成两个部分:一个是数组引用,也就是在代码中定义的数组引用变量;还有一个是实际数组本身,这个部分是运行在系统内存里的,通常无法直接访问它,只能通过数组引用变量来访问它。

    关于数组作为参数传递的问题,可参考以下两篇文章
    指针与数组
    http://blog.csdn.net/ysgjiangsu/article/details/50807406
    二维数组值传递与返回
    http://blog.csdn.net/ysgjiangsu/article/details/50808769

    展开全文
  • 数组在内存中的存储方式 数组的几个要素 数组相关的语法 数组的遍历 数组的相关算法 什么是数组 数组, 一组数据, 一组相同类型的数据. 在内存中, 数组是一串连续的物理空间. 实际上, 数组也是一个变量, 只不过这个...


    目标

    1. 数组在内存中的存储方式
    2. 数组的几个要素
    3. 数组相关的语法
    4. 数组的遍历
    5. 数组的相关算法

    什么是数组

    数组, 一组数据, 一组相同类型的数据. 在内存中, 数组是一串连续的物理空间.

    在这里插入图片描述
    实际上, 数组也是一个变量, 只不过这个变量中存储的是数组首元素的内存地址 由于数组中的元素类型相同 ( 每个格子的大小相同 ), 物理上又是连续的, 所以: 要对数组中的3号元素进行读写, 这样寻址即可:

    3号元素的地址 = 首地址 + 3 * 元素类型大小

    数组的几个要素:

    • 数组名称 ­­­­------表示首地址
    • 数组类型/元素类型
    • 长度/元素个数
    • 元素的值 ( 元素称为Element或Item )
      注意:

    长度一旦确定, 不可改变, length是只读的, 数组的长度是: array.length 元素的下标从0开始,
    最后一个元素的下标是length­1
    数组中的元素通过下标来访问, 但是下标不能超出0­(length­1)的范围, 否则产生越界异常(ArrayIndexOutOfBoundsException).

    语法

    1. 声明数组:
     int[] myArray; // 告诉系统: 我要存储一组int型的数据
    
    1. 分配空间:
     myArray = new int[5]; // 告诉系统: 我需要5个4字节空间, 共20字节
    
    1. 访问数组中的元素 ( 读/写 )
    myArray[3] = 9527; // 把9527写到这个数组的3号元素中 
    int number = myArray[3] * 2; // 读3号元素的值, 参与表达式运算
    

    创建数组的一些特殊语法:
    在这里插入图片描述

    循环遍历数组

    顺序遍历

    1 for(int i = 0; i < 数组名.length; i++) { 
    2  	// i 天生就是数组元素下标! 
    3  	..... 数组名[i] ..... 
    4 }
    

    要注意不能写成 i <= 数组名.length, 会越界!!!

    也可以反向遍历:

    for(int i = 数组名.length‐1; i >= 0; i‐‐) { }
    

    还可以使用foreach方式遍历:
    在这里插入图片描述

    基于数组的常见算法

    排序: 排序算法很多, 冒泡, 快速, 归并, 堆排序, 插入排序, … *
    冒泡排序口诀: N个元素来排队, 两两相比小靠前, 外层循环N­1, 内层循环N­1­i
    在这里插入图片描述
    java中的java.util.Arrays类提供了sort方法对数组进行方便地排序:

    1 Arrays.sort(数组名);

    查找元素:
    如果一个数组是乱序的, 要查找其中的元素, 通常只能循环挨个比较, 但要注意在循环结 束之前, 不要轻易下结论!
    在这里插入图片描述
    如果数组是有序的, 可以使用二分查找法: 直接和中间位置的元素比较, 根据大小关系, 可以直接缩小一半的查找范围

    找最大值/最小值
    打擂台法
    在这里插入图片描述

    展开全文
  • 下面将深入介绍数组在内存中的运行机制。 数组引用变量只是一个引用,这个引用变量可以指向任何有效的内存,只有当该引用指向有效内存后,才可通过该数组变量来访问数组元素。 与所有引用变量相同的是,引用变量是...

    数组是一种引用数据类型,数组引用变量只是一个引用,数组元素和数组变量在内存里是分开存放的。下面将深入介绍数组在内存中的运行机制。

    数组引用变量只是一个引用,这个引用变量可以指向任何有效的内存,只有当该引用指向有效内存后,才可通过该数组变量来访问数组元素。

    与所有引用变量相同的是,引用变量是访问真实对象的根本方式。也就是说,如果我们希望在程序中访问数组,则只能通过这个数组的引用变量来访问它。

    实际的数组元素被存储在堆(heap)内存中;数组引用变量是一个引用类型的变量,被存储在栈(stack)内存中。数组在内存中的存储示意图如图4.2所示

    å¾4.2 æ°ç»å¨åå­ä¸­çå­å¨ç¤ºæå¾

    感谢:https://blog.csdn.net/tianjunjie520/article/details/81164629

    展开全文
  • 二维数组在内存中的存储方式? 二维数组的小标,哪个是行,哪个指列?

    二维数组在内存中的存储方式?



    二维数组的小标,哪个是行,哪个指列?


    展开全文
  • 一、变量 1、定义变量并赋值 int one = 100;//声明一个int型变量 double two = 12.5;//声明一个double型变量
  • 二维数组实际在内存中的存储方式 提示:二维数组也是按照像一维数组那样的存储.注意:如何证明:通过指针来进行访问每一个元素*(*a+1) 1.*a 表示将一个行地址变成该行的首地址(即一个具体元素的地址)) 2.&a[0]...
  • [转载]数组在内存中的存储方式

    万次阅读 2016-03-04 16:40:53
    数组
  • 指针和数组我们之前也谈到了,我们说指针就是地址,对指针解引用就是找到这个地址所指向空间存储的数据。...数组在内存中的存储方式是从低地址往高地址使用,定义一个数组会一次开辟一大块空间,然...
  • SU(Seismic Unix)多维(≥2)数组的存储是列优先(columnmajor)的 CUDA多维数组(≥2)数组的 存储是行优先(row major)的 用SU开的数组,将数据传给CUDA后还是列优先的。
  • 一.数组的创建和初始化1.创建方式: type_t(数组的元素类型) arr_name [const_n] (是一个常量的表达式...一维数组在内存中的存储1.数组在内存中是连续存放的,如果是整型 int 地址差4个字节 访问arr[i], 编译器,...
  • 声明变量的时候,就会在内存中开辟存储空间,而开辟的存储空间,是从大到小开辟的
  • C++ 数组在内存中的分配

    千次阅读 2018-03-09 13:20:40
    接前一篇内容,C++中数组在内存中也有静态分配和动态分配区别。静态数组建立的方式为:A a[],它在栈上分配空间;动态方式是使用new,malloc在堆上分配。 数组要么在静态存储区被创建(如全局数组),要么在栈...
  • 接前一篇内容,C++中数组在内存中也有静态分配和动态分配区别。静态数组建立的方式为:A a[],它在栈上分配空间;动态方式是使用new,malloc在堆上分配。 数组要么在静态存储区被创建(如全局数组),要么在栈或...
  • Java中的数组存储两类事物: 原始值(int,char,...),或者引用(对象指针).当一个对象通过 new 创建,那么将内存中分配一段空间,并且返回其引用(指针).对于数组,也是同样的方式.1. 一维数组[java] view plain ...
  • java数组的存储方式

    2020-07-25 09:48:09
    java数组在内存中的存储方式 数组的引用存在栈中,而数组中的元素都存储在堆中。数组作为一种容器,它在堆中所被分配的是一段连续的空间。用来存放元素,这段连续的空间每一个空间都有下标,下标是连续的对应的! ...

空空如也

空空如也

1 2 3 4 5 ... 20
收藏数 2,508
精华内容 1,003
关键字:

数组在内存中的存储方式