日期:2014-05-17  浏览次数:20863 次

|ZYCWPF| 今天看多线程的,但是对volatile这个关键字不理解,怎么感觉用static不是也是一样的效果吗?
大家帮我说说static和volatile的区别
static我清楚是做什么用的
但volatile什么时候用呢?
谢谢
------最佳解决方案--------------------
volatile修饰的变量无需lock就可以在多线程内共享,它可以有效保证在多个cpu下更新而刷新各自的缓存。volatile的性能更高,它底层会使用cpu的自旋锁指令。
------其他解决方案--------------------
volatile表示数据字段可能被其它线程修改。
比如拿msdn上的例子来说:

public class Worker
{
    private volatile bool _shouldStop;

    public void DoWork()
    {
        while (!_shouldStop)
        {
            Console.WriteLine("Worker thread: working...");
        }
        Console.WriteLine("Worker thread: terminating gracefully.");
    }
}

如果_shouldStop不声明为volatile,编译器优化时就可能省去这个!_shouldStop检查判断,因为它的值始终应该是进行方法时候的那个值,但是加了volatile就不会做这样的优化,循环每次都会去检查,因为它可能被其它线程修改。
------其他解决方案--------------------

public class Worker 
{
     //private volatile bool _shouldStop;
     //上面这语句我感觉改为效果也是一样的啊?所以我看不出作用!谢谢
     public static bool _shouldStop;
     public void DoWork()
     {
         while (!_shouldStop)
         {
             Console.WriteLine("Worker thread: working...");
         }
         Console.WriteLine("Worker thread: terminating gracefully.");
     }
 } 

------其他解决方案--------------------
本帖最后由 caozhy 于 2012-12-04 22:51:17 编辑 多线程程序不要用简单的运行来看效果。你需要在多cpu环境下,反复、大量运行多个线程的程序,并且大量访问共享变量,才能看出来。

不用volatile的话
可能出现如下情况:
如下代码:
_shouldStop = true;
_shouldStop = !_shouldStop;
编译器会转变成这样的代码:
_shouldStop = true;
bool temp = _shouldStop;
temp = !temp; ... 3
_shouldStop = temp;
但是有可能在第三行,这个线程切换了
另一个线程更改了_shouldStop,比如设置为false
但是这个线程再切换的时候不知道,于是将false又写回去了。
------其他解决方案--------------------
看一下这个帖子:
http://stackoverflow.com/questions/133270/illustrating-usage-of-the-volatile-keyword-in-c-sharp/1284007#1284007
我用它的代码也试了,打开优化或release模式下,程序死循环。

msdn自带的例子却产生不了这样的现象,按上面帖子里的解释是编译器越来越聪明,会尽量找出这种可能导致错误的优化而不做优化。