什么是unsafe?
什么是Unsafe? 典型回答 Unsafe是CAS的核心类。因为Java无法直接访问底层操作系统,而是通过本地(native)方法来访问。不过尽管如此,JVM还是开了一个后门,JDK中有一个类Unsafe,它提供了硬件级别的原子操作。 Unsafe是Java中一个底层类,包含了很多基础的操作,比如数组操作、对象操作、内存操作、CAS操作、线程(park)操作、栅栏(Fence)操作,...
什么是Unsafe? 典型回答 Unsafe是CAS的核心类。因为Java无法直接访问底层操作系统,而是通过本地(native)方法来访问。不过尽管如此,JVM还是开了一个后门,JDK中有一个类Unsafe,它提供了硬件级别的原子操作。 Unsafe是Java中一个底层类,包含了很多基础的操作,比如数组操作、对象操作、内存操作、CAS操作、线程(park)操作、栅栏(Fence)操作,...
什么是ThreadLocal,如何实现的? 典型回答 ThreadLocal是java.lang下面的一个类,是用来解决java多线程程序中并发问题的一种途径;通过为每一个线程创建一份共享变量的副本来保证各个线程之间的变量的访问和修改互相不影响; ThreadLocal存放的值是线程内共享的,线程间互斥的,主要用于线程内共享一些数据,避免通过参数来传递,这样处理后,能够优雅的解决一些实...
什么是Java内存模型(JMM)? 典型回答 Java程序是需要运行在Java虚拟机上面的,Java内存模型(Java Memory Model ,JMM)就是一种符合内存模型规范的,屏蔽了各种硬件和操作系统的访问差异的,保证了Java程序在各种平台下对内存的访问都能保证效果一致的机制及规范。 提到Java内存模型,一般指的是JDK 5 开始使用的新的内存模型,主要由JSR-133: ...
什么是CAS?存在什么问题? 典型回答 CAS是一项乐观锁技术,是Compare And Swap的简称,顾名思义就是先比较再替换。CAS 操作包含三个操作数 —— 内存位置(V)、预期原值(A)和新值(B)。在进行并发修改的时候,会先比较A和V中取出的值是否相等,如果相等,则会把值替换成B,否则就不做任何操作。 当多个线程尝试使用CAS同时更新同一个变量时,只有其中一个线程能更新变量...
什么是AQS的独占模式和共享模式? 典型回答 AbstractQueuedSynchronizer(AQS)是Java并发包中的一个核心框架,用于构建锁和其他同步组件。 如何理解AQS? 它提供了一套基于FIFO队列的同步器框架,并支持独占模式和共享模式,这两种模式是用于实现同步组件的关键。 独占模式意味着一次只有一个线程可以获取同步状态。这种模式通常用于实现互斥锁,如R...
为什么虚拟线程尽量避免使用ThreadLocal 典型回答 在使用虚拟线程的时候,不建议使用ThreadLocal,这是JDK官网文档中提到的。 虚拟线程是支持ThreadLocal的,但由于可能创建的虚拟线程数量巨大,不当使用ThreadLocal可能导致内存泄漏等问题。如果需要,可以考虑使用作用域局部变量(Scope-local variables)作为替代方案。 Scoped...
为什么虚拟线程不要和线程池一起用? 典型回答 在JEP425 中,关于虚拟线程的介绍中,多次提到,不要将虚拟线程池化。也就是说,不要把虚拟线程和线程池合着用。 主要原因是:像所有资源池一样,线程池旨在共享昂贵的资源,但虚拟线程并不昂贵,因此永远不需要将它们池化。 虚拟线程被设计为可以轻松地创建和销毁的轻量级实体,旨在允许每个任务都在其自己的虚拟线程中运行。这与传统的平台线程不...
为什么虚拟线程不能用synchronized? 典型回答 Java中的虚拟线程旨在提高并发编程的效率和性能,通过允许创建数以百万计的线程而对系统资源的消耗最小。虚拟线程背后的主要思想是将线程的调度任务从操作系统级别转移到Java虚拟机(JVM)级别,从而减少上下文切换的成本并提高系统的吞吐量。 JDK21 中的虚拟线程是怎么回事? 虚拟线程是在JEP425中提出的,但是JEP425在...
为什么不能在try-catch中捕获子线程的异常? 典型回答 在Java中,主线程不能直接捕获子线程抛出的异常的!主要是因为子线程和主线程是独立的执行单元,它们的执行是并发的,因此主线程无法捕获子线程的异常。子线程的异常通常由子线程自己处理或通过适当的异常处理机制处理。 线程隔离,这也是Java保证线程出现异常不会影响整个进程的一个主要原理。 Java线程出现异常,进程为啥不会退出?...
为什么不建议通过Executors构建线程池 典型回答 Executors类看起来功能还是比较强大的,又用到了工厂模式、又有比较强的扩展性,重要的是用起来还比较方便,如: ExecutorService executor = Executors.newFixedThreadPool(nThreads) ; 即可创建一个固定大小的线程池。 但是为什么在阿里巴巴Java开发手册中也明...