前言:今天不学习,明天变咸鱼
我们都知道创建字符串的方式有两种(基本的创建方式,clone序列化...不考虑)
a.String s1 = "asdf";
b.String s2 = new String("asdf");
我们首先分析下他在内存中的分配情况:
对于s1来说他会在"栈"内存中创建一个引用,之后去"代码区域"中的字符串常量
池中去寻找看看存不存在S1这个引用,如果不存在那么在"字符串常量池"中会有一
个s1的对象,如果存在那么直接将s1的引用指向字符串常量池中即可
也就是说这样:
String s5 = "apple";
String s6 = "apple";
System.out.println(s5 == s6);
System.out.println(s5.equals(s6));
true
true
这样子就解释了为什么s1与s2不相等的原因
在我认为首先内存存放的位置就不一样。一个在s1在常量池中,s2在堆中.所以不
相等.
程序运行时,对象是怎么进行安置的呢?特别内存是内养分配的呢?
首先,你需要知道的是有五个不同的地方可以存储数据
- 1) 寄存器
- 2) 堆栈
- 3) 栈
- 4) 常量存储
- 5) 非RAM存储
分析下我以前的知识储备,如图:
下面是结合书和资料进行了调整以及补充
- 1) 寄存器:这是位于最快的存储区域,因为它位于不同于其他存储区的内部--->处理器内部.但是寄存器数量是极其有限的(如果你学过汇编语言应该清楚寄存
- 器大概有这些:
拿8086CPU来举例:AX,BX,CX,DX,SI,DI,SP,BP,IP,CS,SS,DS,ES,PWS
其中AX,BX,CX,DX这四个寄存器通常用来存放一般性数据.
)跟CPU直接打交道的,速度非常快.按照他们的读取速度可以分为以下几类:
1. 寄存器(Register)
2. 缓存(Cache)
3. 内部存储器(RAM)
4. 外部存储器(Hard Drive)
我们平时所说的内存就是第三类RAM(支持读写).
- 2) 堆栈:位于通用RAM(随机访问存储器中),但是可以通过堆栈指针从处理器那里获得直接支持(这里面透露了一个信息"栈",我们应该都知道"栈"他有两种
方式
a.push() 入栈
b.pop()出栈
且遵循后进先出的原则
)若堆栈指针向下即pop()入栈,标志着要分配新的内存,相反,向上移动则意味着出栈,释放内存.
重点:在创建对象的时候,Java系统必须知道存储在堆栈内所有项(我认为是分别配的地址的引用)的确切生命周期,以便于上下移动.一般情况下,仅
仅是把对象的引用存放在堆栈中.
- 3) 堆:一种通用的内存池(也位于RAM区:RAM Suppoted Read And Write),用于存放Java中所有实际的对象(内存),堆不同于堆栈的好处是:编辑器不
不需要知道存储的数据在堆里面存活多长时间。很灵活,但是为了灵活必须付出一定的代价(开辟内存是十分耗费性能的,因为存在两个问题
1.不知道对象的声明周期,需要调用JVM里面的GC来搞定(但是有的时候并不能及时收回).
2.耗费性能,如果你了解过GC的回收算法,你就会知道会消耗时间去遍历的
),
- 4)常量存储:
下面有一段话
运行时常量池(Runtime Constant Pool)是方法区(Method Area)的一部分,是各线程共享的内存区域。
- 5)非RAM存储:如果数据完全存活于程序之外,那么它可以不受程序任何的控制,在程序没有运行的时候也可以存在.
其中两个基本的例子就是:"持久化对象"和"流"对象.暂时就写到这里面.我需要深度思考.回来继续补充