简体   繁体   English

为什么 Semaphore 实现使用 CAS (U.compareAndSetInt) 而不是等待/通知?

[英]Why the Semaphore implementation uses CAS (U.compareAndSetInt) instead of wait/notify?

I've decided to implement some clasess from the concurrency package from scratch and implemented Semaphore with wait/notify.我决定从头开始实现并发 package 的一些类,并通过等待/通知实现信号量。 It seems very easy and intuitive to do so.这样做似乎非常容易和直观。 When I checked the build in implementation, I saw they complicated it all with CAS (Compare And Swap) technique.当我检查构建实现时,我看到他们使用 CAS(比较和交换)技术使这一切变得复杂。 They did the same for the ReentranceLock implementation.他们为 ReentranceLock 实现做了同样的事情。

Why they decided to do it that way?为什么他们决定这样做? Is it because of performance?是因为性能吗? Maybe I should also avoid wait/notify and use CAS in my applications.也许我也应该避免等待/通知并在我的应用程序中使用 CAS。

public class SemaphoreX {
    private int permits;

    SemaphoreX(int permits){
        this.permits = permits;
    }

    public synchronized void acquire() throws InterruptedException{
        while(permits == 0){
            wait();
        }
        permits--;
    }

    public synchronized void release(){
        permits++;
        notify();
    }
}

You should read the javadocs for AbstractQueuedSynchronizer .您应该阅读AbstractQueuedSynchronizer的 javadocs。

Why they decided to do it that way?为什么他们决定这样做? Is it because of performance?是因为性能吗?

I can't tell you with 100% certainty whether this is about performance.我不能 100% 肯定地告诉你这是否与性能有关。 But it is definitely not all about performance.但这绝对不仅仅与性能有关

You will have noticed that the FairSync and UnfairSync classes used by Semaphore are based on AbstractQueuedSynchronizer .您会注意到Semaphore使用的FairSyncUnfairSync类是基于AbstractQueuedSynchronizer的。 If you look at the API, you will see that it provides richer functionality than you get with Java primitive locks and wait / notify .如果您查看 API,您会发现它提供的功能比您使用 Java 原始锁和wait / notify获得的功能更丰富。 In particular, you will see that it supports fair (FIFO) queuing for threads waiting for events.特别是,您将看到它支持等待事件的线程的公平 (FIFO) 排队。 The primitive wait / notify mechanisms don't provide any guarantees of fairness.原始的等待/通知机制不提供任何公平保证。

Fair queuing is a requirement for a Semaphore created with fair set to true .公平排队是使用fair设置为true创建的Semaphore的要求。

Maybe I should also avoid wait/notify and use CAS in my applications.也许我也应该避免等待/通知并在我的应用程序中使用 CAS。

Possibly.可能。 It depends on what your goals are.这取决于你的目标是什么。

But if your primary goal is performance, then I would recommend NOT trying to re-implement java.util.concurrent... classes.但是,如果您的主要目标是性能,那么我建议不要尝试重新实现java.util.concurrent...类。 Just use the existing classes as they are.只需按原样使用现有的类。

And if one of your goals is get good performance, you cannot be afraid of using complicated techniques to implement the concurrency primitives.如果您的目标之一是获得良好的性能,您就不必害怕使用复杂的技术来实现并发原语。 Or of doing your own performance analysis of different approaches and your own performance measurement.或者对不同的方法和你自己的性能测量进行自己的性能分析。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM