C#多线程:1.lock关键字以及用法

C# lock使用详解 阅读详情

lock 关键字和 Monitor 类都是在 C# 中用于实现互斥锁(Mutex)的机制,用于确保多个线程之间的同步访问共享资源(主要目的是防止多个线程同时修改共享资源,从而避免数据不一致和竞态条件)其中lock关键字主要用于简化对 Monitor 类的使用。lock 语句在进入块时获得指定对象的互斥锁,并在离开块时释放锁。若无需要更精细控制锁的情况,使用lock关键字即可。

使用案例:


abstract class CounterBase
{
    public abstract void Increment();
    public abstract void Decrement();
}

class CounterWithLock:CounterBase
{
    private readonly object _syncRoot = new object();
    public int Count { get; private set;}

    public override void Increment()
    {
        lock (_syncRoot)
            Count++;
    }

    public override void Decrement()
    {
        lock (_syncRoot)
            Count--;
    }
}

class Counter : CounterBase
{
    public int Count { get; private set;}
    public override void Increment()
    {
            Count++;
    }

    public override void Decrement()
    {
            Count--;
    }

这里主要定义了几个类Counter和CounterWithLock,其中后者对某些资源用lock关键字添加了锁。
接下来在Main函数里进行如下试验:

 static void Main(string[] args)
 {
     //不合理计数
     WriteLine("Incorrect counter");
     var c = new Counter();
     var t1 = new Thread(() => TestCounter(c));
     var t2 = new Thread(() => TestCounter(c));
     var t3 = new Thread(() => TestCounter(c));

     t1.Start();
     t2.Start();
     t3.Start();
     //主线程等待三个线程执行完毕
     t1.Join();
     t2.Join();
     t3.Join();

     WriteLine($"Total count: {c.Count}");
     WriteLine("----------------------------------");

     //合理计数
     WriteLine("Correct counter");
     var d = new CounterWithLock();
     var t4 = new Thread(() => TestCounter(d));
     var t5 = new Thread(() => TestCounter(d));
     var t6 = new Thread(() => TestCounter(d));

     t4.Start();
     t5.Start();
     t6.Start();
     //主线程等待三个线程执行完毕
     t4.Join();
     t5.Join();
     t6.Join();

     WriteLine($"Total count: {d.Count}");
 }

 static void TestCounter(CounterBase c)
 {
     for (int i = 0; i < 10000000; i++)
     {
         c.Increment();
         c.Decrement();
     }
 }

调试结果如下:
调试结果
可以看到Counter类因为不存在线程安全,导致Count值并不稳定。多个线程可能会取出同一个Count值接着进行同样的操作并写回,导致可能递增操作和递减操作的数量不匹配,这种情形被称为竞争条件,竞争条件是多线程环境中非常常见的导致错误的原因。为了确保不会发生以上情形,确保当有线程进行尝试改变Count值的时候,其他进程必须等到直到当前进程完成操作。我们可以使用lock关键字来实现这种行为,如CounterWithLock类所示。

C#编程,资源加锁Lock避免多线程时同时操作同一变量造成数据错误的简单用法 lock 的目的: 不想在自己使用的时候别人也使用这段代码。体现在多线程情况下,只允许当前线程执行该代码区域,其他线程等待直到该线程执行结束;这样可以多线程避免同时使用某一方法造成数据混乱。 一般定义如下: private static readonly object obj = new object(); lock(obj) { '''代码块 } 用法 当我们使用线程的时候,效率最高的方式当然是异步,即各个线程同时运行,其间不相互依赖和等待。但当不同的线程都需要访问某个资源的时候,就需要同步机制了。 阅读详情

相关推荐

C#lock用法

C#lock用法

qq_43622870的博客 1895

C# 多线程 知识点概述

C# 多线程常用功能的知识点概述

吴启林的博客 269

聊透多线程编程-线程互斥与同步-11. C# lock关键字实现线程互斥

lock关键字C#中用于确保当一个线程访问某个资源时,其他线程不能同时访问该资源,从而避免了数据竞争和不一致性的问题。它通过提供一种简单的方式实现线程同步,保证多线程环境下共享资源的安全访问。

跟佟格湾一起学习计算机知识吧~ 1051

【经验总结】C#常用线程同步方法应用场景和实现原理

  简单描述volatile,Interlocked,lock,Mutex,Semaphore,Spin lock,AutoResetEvent,ManualResetEvent,ReaderWriterLockSlim,MethodImplAttribute,WaitHandle常用同步机制的原理和使用场景。   volatile只是C#的一个关键字,告诉编译器不能将声明的这个变量进行CPU...

weixin_33739627的博客 203

10 个 C# 关键字和功能

在 Stack Overflow 调查中,C#语言是排名第 5 位的编程语言。它广泛用于创建各种应用程序,范围从桌面到移动设备再到云原生。由于有如此多的语言关键字和功能,对于开发人员来说,要跟上新功能发布的最新信息将是一项艰巨的任务。本文深入探讨了每个 C# 开发人员都应该知道的 10 个 C# 关键字1. Async 和 Await关键词: ,asyncawaitC# 中引入的 and 关键...

1957

描述C#多线程lock关键字

  本文介绍C# lock关键字C#提供了一个关键字lock,它可以把一段代码定义为互斥段(critical section),互斥段在一个时刻内只允许一个线程进入执行,而其他线程必须等待。   每个线程都有自己的资源,但是代码区是共享的,即每个线程都可以执行相同的函数。这可能带来的问题就是几个线程同时执行一个函数,导致数据的混乱,产生不可预料的结果,因此我们必须避免这种情况的发生。 C#...

weixin_33785108的博客 162

C# 中的 Lock 关键字实践指南

Monitor在C#中,Mutex和Semaphore是两种用于线程同步的原语。它们通常用于跨进程共享资源的同步,但也可以在单个应用程序内部使用。MutexMutex(互斥体)是一种同步原语,用于在多个线程或进程之间进行互斥。它确保在任何给定时间只有一个线程可以访问资源或代码段。Mutex可以有名称,这意味着可以创建命名的Mutex,多个进程可以通过该名称共享同一个Mutex。// 创建或打开一个命名的Mutex,false表示如果不存在则创建try。

weixin_36474966的博客 1067

c#-多线程lock用法的经典实例

一、Lock定义 lock 关键字可以用来确保代码块完成运行,而不会被其他线程中断。它可以把一段代码定义为互斥段(critical section),互斥段在一个时刻内只允许一个线程进入执行,而其他线程必须等待。这是通过在代码块运行期间为给定对象获取互斥锁来实现的。 在多线程中,每个线程都有自己的资源,但是代码区是共享的,即每个线程都可以执行相同的函数。这可能带来的问题就是几...

你要明白,任何问题都不是孤立存在的,一定有人曾经遇到过,并且已经有更好的解决办法了,只是我还不知道。我不应该在黑暗中独自前行,去重新发明轮子,也许我的顿悟,只是别人的基本功!我应该要站在巨人的肩膀上,学习更成熟的经验和方法,然后再来解决这个问题 2271

C#lock 关键字

C# 里,lock 关键字

weixin_44939430的博客 1612

C#lock

lock语法是: private object o = new object();//创建一个对象 public void Work() {   lock(o)//锁住这个对象   {     //做一些必须按照顺序做的事情   } } 目的是,在多线程中,使用lock后,能使该代码块按照指定的顺序执行,被lock这块代码已经被其中一个线程访问了,那么另外一个线程只能等待。 理论不明白的话,看下面分解。 1.看此代码,是从上面开始执行,先执行A,再执行B,这就是单线程程序,按照顺序执行的,此时结果

故里2130 3万+

C#多线程编程入门:lock关键字详解

比如两个线程同时修改同一个变量的值,最终结果可能就不是我们预期的了。它的基本思路是:当一个线程进入锁定的代码块时,其他线程必须等待,直到该线程执行完毕退出锁定的代码块。它的在线编辑器响应很快,可以立即看到代码运行结果,而且不需要配置复杂的开发环境。特别是当你想快速验证一个多线程示例时,直接在网页上编写代码就能运行,省去了搭建环境的麻烦。非常简单,只需要一个对象作为锁标识,然后将要保护的代码放在lock块中。锁的范围过大:锁的代码块应该尽可能小,只包含真正需要同步的部分,避免不必要的性能损失。

SnowflakeJaguar14的博客 706

C#学习相关系列之多线程---lock线程锁的用法

本文介绍了多线程lock锁的相关用法lock锁可以保证多线程中依次运行相关代码,保证数据安全

qiaodahua的博客 5698

C# Lock 关键字

我们都知道,lock 关键字可以用来确保代码块完成运行,而不会被其他线程中断。也就是,说在多线程中,使用lock关键字,可以让被lock的对象,一次只被一个线程使用。 lock语句根本使用的就是Monitor.Enter和Monitor.Exit,也就是说lock(this)时执行Monitor.Enter(this),大括号结束时执行Monitor.Ex...

张中华的博客 1744

C#中的Lock关键字

C#中的lock关键字 一、Lock定义 lock 关键字可以用来确保代码块完成运行,而不会被其他线程中断。它可以把一段代码定义为互斥段(critical section),互斥段在一个时刻内只允许一个线程进入执行,而其他线程必须等待。这是通过在代码块运行期间为给定对象获取互斥锁来实现的。 在多线程中,每个线程都有自己的资源,但是代码区是共享的,即每个线程都可以执行相同的函数。这可能...

以梦为马 不负韶华 862

浅析 C# Lock

Lock的定义以及概念 实现线程同步的第一种方式是我们经常使用的lock关键字,它将包围的语句块标记为临界区,这样一次只有一个线程进入临界区并执行代码。下面第一段的几行代码是关于lock关键字的使用方式,但更重要的是我们可以通过这个例子来看到lock关键字的本质。第二段是这个方法的IL指令集,从中可以看到lock其实也是一个语法糖,它的内部实现是采用了监视器Monitor。 lock...

TimTiny的博客 6647

C#中public函数的用法_c#多线程lock用法的经典实例

c#初学-多线程lock用法的经典实例一、Lock定义 lock 关键字可以用来确保代码块完成运行,而不会被其他线程中断。它可以把一段代码定义为互斥段(critical section),互斥段在一个时刻内只允许一个线程进入执行,而其他线程必须等待。这是通过在代码块运行期间为给定对象获取互斥锁来实现的。 在多线程中,每个线程都有自己的资源,但是代码区是共享的,即每个线程...

weixin_39725154的博客 610

[C#]线程lock用法

1. lock(this)的缺点就是在一个线程(例如本例的t1)通过执行该类的某个使用"lock(this)"的方法(例如本例的LockMe())锁定某对象之后, 导致整个对象无法被其他线程(例如本例的主线程)访问 - 因为很多人在其他线程(例如本例的主线程)中使用该类的时候会使用类似lock(c1)的代码。,Lock区域内的代码表示临界区,使得同一时间只有一个线程能够进入Lock所包含的函数中,实现原子操作,保护同一资源只有一个线程进行修改,实现不同线程中数据的同步。Lock可以看成在操作系统中的。

FL1768317420的博客 1442
上一篇: C#高效编程:(第一章:语言习惯 1. 属性以及一个简单索引器的实现)
下一篇: C#高效编程:(第一章:语言习惯 2. 优先考虑查询语法(query syntax)而不是循环结构)
Man_Lucifer
博客等级 码龄8年 18粉丝 · 7原创
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值