数组和链表与栈和队列之间的关系及堆和栈之间的关系

本屌最近在学习数据结构过程中,由于连续看了数组,栈,队列,链表等,一时混杂,下面摘取参考资料,供自己学习使用。
第一部分:介绍了数据存储结构和数据结构的区别,以及链表和数组的差异。
第二部分:介绍了堆和栈的区别。
(1)数据存储结构:计算机的一个概念,描述数据在计算机中存储方式;常用的数据存储方式就两种:顺序存储,非顺序存储!

顺序存储就是把数据存储在一块连续的存储介质(比如硬盘或内存)上----举个例子:从内存中拿出第100个字节到 1000个字节间的连续位置,存储数据;数组就是典型的顺序存储!

非顺序存储就是各个数据不一定存在一个连续的位置上,只要每个数据知道它前面的数据和后面的数据,就能把所有数据连续起来啦;链表就是典型的非顺序存储啦!

数据结构:是指相互之间存在一种或多种特定关系的数据元素的集合。听起来是不是很抽象,简单理解:数据结构就是描述对象间逻辑关系的学科。比如:队列就是一种先进先出的逻辑结构,栈是一种先进后出的逻辑结构,家谱 是一种树形的逻辑结构!(初学数据结构的时候很不理解为什么有“栈”这个东西;队列很容易理解—无论购物就餐都需要排队;栈可以认为就是个栈道— 只允许一个人通过的小道,而且只能从一端进入,然后再从这端返回,比如你推了个箱子进去啦,第二个人也推个箱子进去,此时只能等后进来的这个人拉着箱子出 去后,你才能退出。)

队列、栈是线性数据结构的典型代表,而数组、链表是常用的两种数据存储结构;队列和栈均可以用数组或链表的存储方式实现它的功能!

数组属于顺序存储,由于每个元素的存储位置都可以通过简单计算得到,所以访问元素的时间都相同(直接访问数组下标);链表属于数据的链接存储,由于每个元素的存储位置是保存在它的前驱或后继结点中的,所以只有当访问到其前驱结点或后继结点后才能够按指针访问到自己,访问任一元素的时间与该元素结点在链接存 储中的位置有关。

链表和数组的区别:

链表和数组是常用的两种数据存储结构,都能用来保存特定类型的数据。两者存在着一些差异:

1.占用的内存空间

链表存放的内存空间可以是连续的,也可以是不连续的,数组则是连续的一段内存空间。一般情况下存放相同多的数据数组占用较小的内存,而链表还需要存放其前驱和后继的空间。

2.长度的可变性

链表的长度是按实际需要可以伸缩的,而数组的长度是在定义时要给定的,如果存放的数据个数超过了数组的初始大小,则会出现溢出现象。

3.对数据的访问

链表方便数据的移动而访问数据比较麻烦;数组访问数据很快捷而移动数据比较麻烦。

链表和数组的差异决定了它们的不同使用场景,如果需要很多对数据的访问,则适合使用数组;如果需要对数据进行很多移位操作,则设和使用链表。

(2)堆和栈有什么区别

1.栈(Stack)是操作系统在建立某个进程时或者线程(在支持多线程的操作系统中是线程)为这个线程建立的存储区域,该区域具有FIFO的特性,在编译的时候可以指定需要的Stack的大小。在编程中,例如C/C++中,所有的局部变量都是从栈中分配内存空间,实际上也不是什么分配,只是从栈顶向上用就行,在退出函数的时候,只是修改栈指针就可以把栈中的内容销毁,所以速度最快。

2.堆(Heap)是应用程序在运行的时候请求操作系统分配给自己内存,一般是申请/给予的过程,C/C++分别用malloc/New请求分配Heap,用free/delete销毁内存。由于从操作系统管理的内存分配所以在分配和销毁时都要占用时间,所以用堆的效率低的多!但是堆的好处是可以做的很大,C/C++对分配的Heap是不初始化的。

3.在Java中除了简单类型(int,char等)都是在堆中分配内存,这也是程序慢的一个主要原因。但是跟C/C++不同,Java中分配Heap内存是自动初始化的。在Java中所有的对象(包括int的wrapper Integer)都是在堆中分配的,但是这个对象的引用却是在Stack中分配。也就是说在建立一个对象时从两个地方都分配内存,在Heap中分配的内存实际建立这个对象,而在Stack中分配的内存只是一个指向这个堆对象的指针(引用)而已。

4.堆是在程序运行时,而不是在程序编译时,申请某个大小的内存空间。即动态分配内存,对其访问和对一般内存的访问没有区别。{堆是指程序运行时申请的动态内存,而栈只是指一种使用堆的方法(即先进后出)。}

5.栈是先进后出的,但是对于堆而言却没有这个特性,两者都是存放临时数据的地方。 对于堆,我们可以随心所欲的进行增加变量和删除变量,不要遵循什么次序,只要你喜欢。


从变量存储方面来看堆和栈的区别:

*程序的局部变量存在于(栈)中,全局变量存在于(静态区 )中,动态申请数据存在于( 堆)中;

*这样说比较准确,所谓的栈其实是由寄存器ebp和esp指向的一片内存空间(ebp指向栈底,esp指向栈顶),原则上是由高地址向低地址生长的一片空间,会保存一些临时的数据,比如一个函数中的临时变量以及返回地址,数据的出入是先进后出,后进先出.

*全局变量实际上是存在一个(一般来说正常的编译器)可读可写的内存空间,这个空间是在你写程序编译好的空间地址(由编译器决定),是固定的.

*堆是由操作系统管理的一片空间,事先是没有在进程空间里分配的(比如你在没有分配堆的时候就访问堆空间会报一个内存访问错误),一般是由程序动态的分配出来,一旦分配了以后,一般需要程序去释放自己的堆空间.

*堆,用于保存new 和malloc这些自定义的内存变量;
*全局静态区用于保存全局变量和静态变量;
*字符常量区,用于保存字符串;
*代码区,用于保存程序的二进制代码;

原文链接:https://blog.csdn.net/Whatssssup/article/details/78227907

  • 0
    点赞
  • 5
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值