C# 编程中互斥锁的使用

news2024/12/23 5:10:27

C# 中的互斥锁

互斥锁是 C# 中使用的同步原语,用于控制多个线程或进程对共享资源的访问。其目的是确保在任何给定时间只有一个线程或进程可以获取互斥锁,从而提供互斥。

C# 中互斥锁的优点

可以使用互斥锁 (Mutex) 并享受其带来的好处。

1. 共享资源的独占访问

  • 场景:多个线程或进程需要独占访问共享资源(例如文件、数据库或硬件设备)的情况。
  • 示例:考虑一个多线程应用程序,其中多个线程需要同时写入共享日志文件。
  • 好处: 利用互斥锁,可以保证一次只有一个线程或进程可以访问资源,从而防止数据损坏或竞争条件。

2.跨进程同步

  • 场景:不同进程中运行的线程之间需要同步。
  • 示例:协调多个进程对共享内存映射文件的访问。
  • 好处:互斥锁可以被命名并在整个系统范围内使用,从而实现跨进程边界的同步。

3. 关键部分保护

  • 场景:代码的关键部分需要防止被多个线程并发执行的情况。
  • 示例:考虑一个缓存实现,其中添加或删除项目必须是线程安全的。
  • 好处:通过使用互斥锁,它有助于对关键部分的访问进行序列化,确保一次只有一个线程执行受保护的代码,从而避免竞争条件。

4. 资源池化

  • 场景:管理对有限资源池(例如数据库连接或网络套接字)的访问时。
  • 示例:多个线程竞争可用连接的连接池。
  • 好处:可以使用互斥锁 (Mutex) 来控制对池的访问,从而保证同时使用的用户数量不超过池的容量。

5.避免死锁

  • 场景:在多个同步原语一起使用以防止发生死锁的情况下。
  • 示例:实现一个需要原子锁定多个资源的事务系统。
  • 好处:互斥锁可以参与死锁避免策略,有助于防止死锁情况的发生。

互斥锁的实现

步骤1.

使用Xaml View测试所有情况。

<Window x:Class="MutexExample.MainWindow"
        xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
        xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
        xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
        xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
        xmlns:local="clr-namespace:MutexExample"
        mc:Ignorable="d"
        Title="MainWindow" Height="450" Width="800">
    <Grid>
        <StackPanel Orientation="Vertical">
            <Button x:Name="BtnSR" Height="30" Content="Shared Resource" Margin="10" Click="BtnSR_Click"/>
            <Button x:Name="BtnCPS" Height="30" Content="Cross-Process Synchronization" Margin="10" Click="BtnCPS_Click"/>
            <Button x:Name="BtnCSP" Height="30" Content="Critical Section Protection" Margin="10" Click="BtnCSP_Click"/>
            <Button x:Name="BtnRP" Height="30" Content="Resource Pooling" Margin="10" Click="BtnRP_Click"/>
            <Button x:Name="BtnDLA" Height="30" Content="Deadlock Avoidance" Margin="10" Click="BtnDLA_Click"/>
        </StackPanel>
    </Grid>
</Window>

后端编程

using System;
using System.Threading;
using System.Windows;

namespace MutexExample
{
    public partial class MainWindow : Window
    {
        Mutex mutex = new Mutex();
        static int availableResources = 3;

        public MainWindow()
        {
            InitializeComponent();
        }

        private void SharedResourceAccess(object id)
        {
            mutex.WaitOne(); // Acquire the mutex
            try
            {
                Console.WriteLine($"Thread {id} is accessing the shared resource...");
                // Simulate some work
                Thread.Sleep(2000);
            }
            finally
            {
                mutex.ReleaseMutex(); // Release the mutex
            }
        }

        private void BtnSR_Click(object sender, RoutedEventArgs e)
        {
            // Create multiple threads accessing the shared resource
            for (int i = 0; i < 5; i++)
            {
                Thread thread = new Thread(SharedResourceAccess);
                thread.Start(i);
            }
        }

        private void BtnCPS_Click(object sender, RoutedEventArgs e)
        {
            // Acquire the mutex
            if (mutex.WaitOne(TimeSpan.FromSeconds(5)))
            {
                try
                {
                    Console.WriteLine("Process 1 has acquired the mutex.");
                    Console.ReadLine(); // Hold the mutex until Enter is pressed
                }
                finally
                {
                    mutex.ReleaseMutex(); // Release the mutex
                }
            }
            else
            {
                Console.WriteLine("Process 1 failed to acquire the mutex.");
            }
        }

        private void CriticalSectionAccess(object id)
        {
            mutex.WaitOne(); // Acquire the mutex
            try
            {
                Console.WriteLine($"Thread {id} is executing the critical section...");
                // Simulate some work
                Thread.Sleep(2000);
            }
            finally
            {
                mutex.ReleaseMutex(); // Release the mutex
            }
        }

        private void BtnCSP_Click(object sender, RoutedEventArgs e)
        {
            // Create multiple threads accessing a critical section
            for (int i = 0; i < 5; i++)
            {
                Thread thread = new Thread(CriticalSectionAccess);
                thread.Start(i);
            }
        }

        private void ResourceAccess(object id)
        {
            mutex.WaitOne(); // Acquire the mutex
            try
            {
                if (availableResources > 0)
                {
                    availableResources--;
                    Console.WriteLine($"Thread {id} acquired a resource. Remaining resources: {availableResources}");
                    // Simulate some work
                    Thread.Sleep(2000);
                    availableResources++;
                }
                else
                {
                    Console.WriteLine($"Thread {id} could not acquire a resource. No resources available.");
                }
            }
            finally
            {
                mutex.ReleaseMutex(); // Release the mutex
            }
        }

        private void BtnRP_Click(object sender, RoutedEventArgs e)
        {
            // Create multiple threads to access the resource pool
            for (int i = 0; i < 5; i++)
            {
                Thread thread = new Thread(ResourceAccess);
                thread.Start(i);
            }
        }

        private void BtnDLA_Click(object sender, RoutedEventArgs e)
        {
            Thread thread1 = new Thread(Thread1);
            Thread thread2 = new Thread(Thread2);

            thread1.Start();
            thread2.Start();

            thread1.Join();
            thread2.Join();
        }

        private Mutex mutex1 = new Mutex();
        private Mutex mutex2 = new Mutex();

        private void Thread1()
        {
            mutex1.WaitOne();
            Console.WriteLine("Thread 1 acquired mutex1");

            Thread.Sleep(1000);

            mutex2.WaitOne();
            Console.WriteLine("Thread 1 acquired mutex2");

            mutex2.ReleaseMutex();
            mutex1.ReleaseMutex();
        }

        private void Thread2()
        {
            mutex2.WaitOne();
            Console.WriteLine("Thread 2 acquired mutex2");

            Thread.Sleep(1000);

            mutex1.WaitOne();
            Console.WriteLine("Thread 2 acquired mutex1");

            mutex1.ReleaseMutex();
            mutex2.ReleaseMutex();
        }
    }
}

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/1891707.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

使用 PCA 可视化数据的分类能力

使用 PCA 探索数据分类的效果&#xff08;使用 Python 代码&#xff09; 「AI秘籍」系列课程&#xff1a; 人工智能应用数学基础人工智能Python基础人工智能基础核心知识人工智能BI核心知识人工智能CV核心知识 主成分分析 (PCA) 是数据科学家使用的绝佳工具。它可用于降低特征…

LabVIEW自动探头外观检测

开发了一套基于LabVIEW的软件系统&#xff0c;结合视觉检测技术&#xff0c;实现探头及连接器外观的自动检测。通过使用高分辨率工业相机、光源和机械手臂&#xff0c;系统能够自动定位并检测探头表面的细微缺陷&#xff0c;如划痕、残胶、异色、杂物等。系统支持多种探头形态&…

机器学习简介--NLP(二)

机器学习简介 机器学习简介机器学习例子机器学习分类有监督学习有监督学习的应用 无监督学习 机器学习常见概念数据集k折交叉验证过拟合欠拟合评价指标 机器学习简介 机器学习例子 问题&#xff1a; 2&#xff0c;4&#xff0c;6&#xff0c;8&#xff0c;&#xff1f;&#…

智能语音门锁:置入NV170D语音芯片ic 打造便捷生活新体验

一、智能门锁语音芯片开发背景 随着科技的飞速发展&#xff0c;传统门锁的局限性日益凸显&#xff0c;无法满足现代人对高效、安全生活的需求。在这样的时代背景下&#xff0c;智能门锁应运而生&#xff0c;它不仅继承了传统门锁的基本功能&#xff0c;更通过融入先进的科技元素…

数据库安全:MySQL权限体系划分与实战操作

「作者简介」&#xff1a;冬奥会网络安全中国代表队&#xff0c;CSDN Top100&#xff0c;就职奇安信多年&#xff0c;以实战工作为基础著作 《网络安全自学教程》&#xff0c;适合基础薄弱的同学系统化的学习网络安全&#xff0c;用最短的时间掌握最核心的技术。 这一章节我们需…

基于OpenMV识别数字及程序说明

OpenMV简介 OpenMV是一个开源、低成本且功能强大的机器视觉模块。它基于STM32F427CPU&#xff0c;集成了OV7725摄像头芯片&#xff0c;能在小巧的硬件模块上&#xff0c;用C语言高效地实现核心机器视觉算法&#xff0c;并提供了Python编程接口&#xff0c;使得图像处理的复杂度…

k8s_集群搭建_k8s管理前端_dashboard安装部署---分布式云原生部署架构搭建017

然后再去安装一下一个dashboard,有了这个以后,操作k8s集群就不用 一直敲命令了 可以看到上面的命令拿过来,然后 执行就可以了 然后如果执行慢,可以直接先去下载,使用wget,然后再去 也可以在浏览器访问,把内容拿到,然后 下面是内容: # Copyright 2017 The Kubernetes Author…

金融科技企业的数据治理与合规挑战

随着科技的发展&#xff0c;金融科技行业在我国得到了迅猛发展。金融科技创新不仅为消费者带来了便捷的金融服务&#xff0c;也极大地提高了金融行业的运营效率。然而&#xff0c;在金融科技发展的同时&#xff0c;数据治理与合规挑战也日益显现。本文将深入探讨金融科技企业在…

84 柱状图中最大的矩形

题目 给定 n 个非负整数&#xff0c;用来表示柱状图中各个柱子的高度。每个柱子彼此相邻&#xff0c;且宽度为 1 。 求在该柱状图中&#xff0c;能够勾勒出来的矩形的最大面积。 示例 输入&#xff1a;heights [2,1,5,6,2,3] 输出&#xff1a;10 解释&#xff1a;最大的矩…

华为OD机试 - 最长合法表达式 - 双指针(Java 2024 D卷 100分)

华为OD机试 2024D卷题库疯狂收录中&#xff0c;刷题点这里 专栏导读 本专栏收录于《华为OD机试&#xff08;JAVA&#xff09;真题&#xff08;D卷C卷A卷B卷&#xff09;》。 刷的越多&#xff0c;抽中的概率越大&#xff0c;每一题都有详细的答题思路、详细的代码注释、样例测…

竞赛选题 交通目标检测-行人车辆检测流量计数 - 竞赛选题

文章目录 0 前言1\. 目标检测概况1.1 什么是目标检测&#xff1f;1.2 发展阶段 2\. 行人检测2.1 行人检测简介2.2 行人检测技术难点2.3 行人检测实现效果2.4 关键代码-训练过程 最后 0 前言 &#x1f525; 优质竞赛项目系列&#xff0c;今天要分享的是 &#x1f6a9; 毕业设计…

苹果Mac电脑能玩什么游戏 Mac怎么运行Windows游戏

相对于Windows平台来说&#xff0c;Mac电脑可玩的游戏较少。虽然苹果设备的性能足以支持各种大型游戏&#xff0c;但由于系统以及苹果配套服务的限制&#xff0c;很多游戏无法在Mac系统中运行。不过&#xff0c;借助虚拟机软件&#xff0c;Mac电脑可以突破系统限制玩更多的游戏…

Python | Leetcode Python题解之第213题打家劫舍II

题目&#xff1a; 题解&#xff1a; class Solution:def rob(self, nums: List[int]) -> int:def robRange(start: int, end: int) -> int:first nums[start]second max(nums[start], nums[start 1])for i in range(start 2, end 1):first, second second, max(fi…

Rural Access Index (RAI)农村通达指数

农村通达指数&#xff08;RAI&#xff09; 简介 农村通达指数&#xff08;RAI&#xff09;是全球交通领域最重要的发展指标之一。它是目前可持续发展目标中唯一一个直接衡量农村通达性的指标&#xff0c;通过评估农村人口的四季道路通达性来实现。在 2015 年作为可持续发展目…

二手物品交易小程序的设计

管理员账户功能包括&#xff1a;系统首页&#xff0c;个人中心&#xff0c;用户管理&#xff0c;管理员管理&#xff0c;商品信息管理&#xff0c;论坛管理&#xff0c;收货地址管理&#xff0c;基础数据管理 微信端账号功能包括&#xff1a;系统首页&#xff0c;商品信息&…

币界网讯,预计以太坊现货 ETF 将于 7 月中旬推出

刚刚 ETF Store 总裁 Nate Geraci 在 X &#xff08;前Twitter&#xff09;平台上宣布&#xff0c;备受数字货币市场期待的SEC以太坊现货 ETF提案&#xff0c;将于7 月中旬通过美国证券交易委员会&#xff08;SEC&#xff09;批准。Nate Geraci透露修订后的 S-1 文件将于 7 月 …

Java高级重点知识点-20-File

文章目录 File类 File类 java.io.File 类是文件和目录路径名的抽象表示&#xff0c;主要用于文件和目录的创建、查找和删除等操作。 基本方法 构造方法&#xff1a; public File(String pathname) &#xff1a;通过将给定的路径名字符串转换为抽象路径名来创建新的 File实例…

文章解读与仿真程序复现思路——电网技术EI\CSCD\北大核心《基于目标鲁棒的电动汽车及基站储能联合参与电力市场的决策模型 》

本专栏栏目提供文章与程序复现思路&#xff0c;具体已有的论文与论文源程序可翻阅本博主免费的专栏栏目《论文与完整程序》 论文与完整源程序_电网论文源程序的博客-CSDN博客https://blog.csdn.net/liang674027206/category_12531414.html 电网论文源程序-CSDN博客电网论文源…

SpringCloud进阶篇

文章目录 网关快速入门创建模块引入依赖修改启动类配置路由路由过滤(一般不用) 自定义GlobalFilter登录校验登录校验过滤器 微服务获取用户信息保存用户信息到请求头拦截器获取用户信息 OpenFeign传递用户信息配置共享添加共享配置拉取共享配置 配置热更新添加配置到Nacos配置热…

#LinuxC高级 笔记二

makefile gcc gdb makefile 1. 分文件编程 1.1 源文件&#xff1a;.c结尾的文件 包含main函数的.c 包含子函数的.c 1.2 头文件&#xff1a;.h结尾的文件 头文件、宏定义、typedef 、结构体、共用体、枚举、函数声明 include引用时“”和<>的区别&#xff1a; <>去系…