Are volatile variables useful? If yes then when?

前端 未结 3 1047
长情又很酷
长情又很酷 2021-02-19 08:36

Answering this question made me think about something is still not clear for me. Let\'s first assume we read all from this post and this post.

[begin edit] Mayb

3条回答
  •  星月不相逢
    2021-02-19 09:15

    Volatile variables could theortically be useful with code like the following:

    while (myVolatileFlag)
        ...
    

    If myVolatileFlag is declared as a volatile bool, it will prevent the compiler from caching its value and assuming that it won't change during the loop. (However, it's actually rather hard to write some code that actually demonstrates the difference that applying volatile makes.)

    From http://msdn.microsoft.com/en-us/LIBRARY/x13ttww7%28v=vs.80%29.aspx

    The volatile keyword indicates that a field might be modified by multiple concurrently executing threads. Fields that are declared volatile are not subject to compiler optimizations that assume access by a single thread. This ensures that the most up-to-date value is present in the field at all times.

    Here's an example program that demonstrates the issue:

    using System;
    using System.Threading;
    using System.Threading.Tasks;
    
    namespace Demo
    {
        internal class Program
        {
            private void run()
            {
                Task.Factory.StartNew(resetFlagAfter1s);
                int x = 0;
    
                while (flag)
                    ++x;
    
                Console.WriteLine("Done");
            }
    
            private void resetFlagAfter1s()
            {
                Thread.Sleep(1000);
                flag = false;
            }
    
            private volatile bool flag = true;
    
            private static void Main()
            {
                new Program().run();
            }
        }
    }
    

    Run a "Release" build of the above program, and it will terminate after one second. Remove the volatile modifier from volatile bool flag, and it will never terminate.

    Volatile Locals

    Generally speaking, volatile is not needed for locals because the compiler can see if you are modifying a local, or are passing a reference to the local to another method. In both cases the compiler will assume that the value is being changed, and will disable optimizations that depend on the value not changing.

    However, with later versions of C# with Lambdas etc, things aren't quite so clear-cut. See the reply from Eric Lippert in this thread.

提交回复
热议问题