Is there a synchronization class that guarantee FIFO order in C#?

前端 未结 7 1600
无人共我
无人共我 2020-11-28 11:01

What is it and how to use?

I need that as I have a timer that inserts into DB every second, and I have a shared resource between timer handler and the main thread. I

7条回答
  •  野性不改
    2020-11-28 11:15

    Follow up on Matthew Brindley's answer.

    If converting code from

    lock (LocalConnection.locker) {...}
    

    then you could either do a IDisposable or do what I did:

    public static void Locking(Action action) {
      Lock();
      try {
        action();
      } finally {
        Unlock();
      }
    }
    
    LocalConnection.Locking( () => {...});
    

    I decided against IDisposable because it would creates a new invisible object on every call.

    As to reentrancy issue I modified the code to this:

    public sealed class QueuedLock {
        private object innerLock = new object();
        private volatile int ticketsCount = 0;
        private volatile int ticketToRide = 1;
        ThreadLocal reenter = new ThreadLocal();
    
        public void Enter() {
            reenter.Value++;
            if ( reenter.Value > 1 ) 
                return;
            int myTicket = Interlocked.Increment( ref ticketsCount );
            Monitor.Enter( innerLock );
            while ( true ) {
                if ( myTicket == ticketToRide ) {
                    return;
                } else {
                    Monitor.Wait( innerLock );
                }
            }
        }
    
        public void Exit() {
            if ( reenter.Value > 0 ) 
                reenter.Value--;
            if ( reenter.Value > 0 ) 
                return;
            Interlocked.Increment( ref ticketToRide );
            Monitor.PulseAll( innerLock );
            Monitor.Exit( innerLock );
        }
    }
    

提交回复
热议问题