当前位置: 首页 > 网络应用技术

Java采访:为什么Java内存模型需要?

时间:2023-03-07 00:53:08 网络应用技术

  访调员:我想与您谈谈今天的Java内存模型。您了解这件作品吗?

  候选人:好吧,让我简要地谈论我的理解。

  访调员:开始您的表演。

  候选人:然后让我首先谈论背景

  候选人:1。现有的计算机通常是多核的,每个核心的高速缓存。L1和L2缓存通常是“每个核心独家”。

  候选人:2。为了提高CPU以提高运营效率,处理器可能对输入代码执行“无序执行”,这是SO所谓的“指令重分类”

  候选人:3。该值的修改操作通常是非原子的(例如,在执行计算机时,I ++实际上分为多个指令)

  候选人:永远,上面不会有任何问题,因为单程意味着没有合并。在单个线程中,编译器/运行时/处理器必须符合AS-IF serif-serial语义,而AS-IF则必须意味着他们不会对“数据依赖性操作”进行排序。

  候选人:为了提高效率,CPU具有高速缓存,分类的说明等,整个架构变得复杂。我们编写的过程还必须“完全”使用CPU资源!因此,我们已经使用过多线程线程

  候选人:多线程表示并发,并发意味着我们需要考虑线程安全问题

  候选人:1。缓存数据不一致:多个线程同时修改“共享变量”。CPU核心下的高速缓存是“未共享”。我该怎么做才能同步多缓存和内存之间的数据?

  候选人:2。多线程中的CPU指令重分类将导致代码以非指望执行,并最终导致结果错误。

  候选人:针对“缓存不一致”的问题,CPU也具有解决方案。通常每个人都知道两种类型:

  候选人:1。使用“总线锁”:在修改数据的过程中,其他内核无法修改内存中的数据(类似于独家内存的概念,只要有CPU修改,其他CPU就具有等待当前的CPU版本)

  候选人:2。缓存一致性协议(MESI协议实际上,有很多协议,但您可能已经看到了).Mesi拆卸英语(修改后的状态),独家(独家状态),共享

  候选人:我认为可以将缓存一致性协议理解为“缓存锁”,该协议的目的是“缓存线“锁”。所谓的“缓存线”实际上是高速缓存存储的最小单元。

  访调员:嗯...

  候选人:MESI协议的原理可能是:当每个CPU读取和共享变量时,将识别数据的“对象状态”(无论修改,共享还是无效)。

  候选人:如果是独家,则意味着将获得当前的CPU。

  候选人:如果共享,则意味着CPU将获得的当前变量数据仍然是最新的。其他CPU同时读取,但尚未修改

  候选人:如果对其进行了修改,则意味着当前的CPU正在修改变量的值,同时,它将将数据状态发送到其他CPU,以通知自己,因为无效(无效),无效(无效),当前的CPU将将高速缓存数据写入主内存,并将其自己的状态从修改更改为独家(独家)(独家)

  候选人:如果它无效,则意味着当前数据已更改,并且需要从主内存再次读取最新数据。

  候选人:实际上,MESI协议确实可以判断“对象状态”并根据“对象状态”制定不同的策略。关键是CPU在修改数据时需要“同步”其他CPU,表明数据表明数据表明数据我已经被我修改了,您不能再使用它了。

  候选人:与“总线锁”相比,MESI协议的“锁定大小”甚至更小,而且性能肯定会更高

  访调员:但据我所知,CPU仍在优化,您仍然知道吗?

  候选人:嗯,我仍然知道一点。

  候选人:从前面提到的情况下,可以发现,当CPU修改数据时,您需要“同步”以告诉其他CPU并等待其他CPU响应tolive。

  候选人:同步意味着等待,等待一无所有。CPU绝对不愿意,因此我再次对其进行了优化。

  候选人:优化是从“同步”到“异步”。

  候选人:“同步”将在修改时告诉其他CPU,现在最新的修改值将写入“商店缓冲区”,并通知其他CPU记住要更改状态,然后CPU直接返回其他内容,直到等待直到等待其他CPU发送的响应消息,然后将数据更新为高速缓存。

  候选人:当其他CPU收到无效的通知时,他们还将将收到的消息放入“无效队列”中。只要“无效队列”将直接写成“无效”

  候选人:异步会带来新的问题:然后,我现在在修改CPU后,我写了“商店缓冲区”,CPU可以做其他事情。最后修改的时间仍在“商店缓冲区”中,并且尚未将其修改为高速缓存。

  候选人:因此,当读取CPU时,您需要转到“商店缓冲区”才能看到存在存在,并且存在直接采用。

  候选人:好的,解决第一个异步带来的问题。(相同的核心读取和写入数据。由于其异步,二读可能仍然是旧值,因此先读取“商店缓冲区”。

  访调员:还有其他吗?

  候选人:当然,然后“异步”会引起相同的核心读取,编写和共享变量的问题,当然,它也会导致“不同的”核心读取和写入共享变量。

  候选人:CPU1修改了A值。修改后的值已写入“商店缓冲区”,并通知CPU2以操作此值的值。CPU2的操作仍然是旧值。

  候选人:即使CPU2收到了推断通知,CPU1的值尚未写入主内存,那么当CPU2再次读取到主内存时,它仍然是旧值...

  候选人:变量之间的多次具有“相关性”(a = 1; b = 0; b = a),这对CPU ...没有感知...

  候选人:总的来说,因为CPU对“缓存共同协议”“商店缓冲区”和“无效队列”的异步优化可能导致以下指令无法找到上一项指令的执行结果(执行每个指令执行(每项执行)执行每个指令的非代码执行序列的顺序),此现象通常称为“ CPU混乱订单执行”

  候选人:为了解决混乱问题(也可以理解为可见的问题,修改尚未与其他CPU同步),并且“内存屏障”的概念也被导致了“记忆”的概念障碍”。

  访调员:嗯...

  候选人:“内存屏障”实际上是为了解决“异步优化”的问题,该问题导致“ CPU混乱”/“ CACHE在时间上不可见”。那么如何解决它?好吧,是要禁止“异步优化”“ drop”(:

  候选人:记忆障碍可以分为三种类型:编写障碍,阅读障碍和所有障碍(包括读写障碍)。可以简要理解障碍物:当操作数据时,将“特殊说明”插入数据中。只要遇到此说明,就必须“完成”以前的操作。

  候选人:然后编写一个障碍以理解这一点:当CPU找到编写障碍的指令时,该说明将在“商店缓冲区”中存在于“商店缓冲区”中的所有指令中,并将其用于高速缓存。

  候选人:通过这种方式,CPU修改的数据可以立即暴露于其他CPUSEN,以实现“写作操作”的可见效果。

  候选人:障碍也相似:当CPU找到阅读障碍的说明时,将在“无效队列”的指示中存在指令的说明。

  候选人:通过这种方式,当前的CPU缓存状态可以准确。当“阅读操作”必须读取最新效果时。

  候选人:由于不同CPU架构的缓存系统不同,因此缓存一致性协议不同,重型排序的策略是不同的,并且内存屏障指令也不同,以简化Java Developers.java的工作。一组规格。这组规格是“ Java内存模型”

  候选人:详细说明,“ Java模型”希望阻止对各种硬件和操作系统访问的差异,以确保Java程序可以与各个平台下的内存访问一致。目的是解决原子能,可见度(缓存一致性)和多线程存在的有序问题。

  访调员:您不简单地谈论Java内存模型的规格和内容吗?

  候选人:不,恐怕聊天是一个下午,下次聊天吗?

  本文的摘要:

  欢迎来到微信公共帐户[Java3y]来谈论Java访谈,而Line Thgracker系列仍在更新!