C# 语言的多线程编程,完全是本科OS里的知识
基本知识,无参数Thread和带参数的Thread
Thread类的参数就是参数指针,可以传入一个无参的函数。
如果要传入带参数的函数,先new一个ParameterizedThreadStart委托实例,带参数的函数名作为它的参数。带参数的函数必须且只能有一个object参数。参考下面的
ConterWithParam(object param)
static int iCnt = ;
static readonly int N = ; static void Main(string[] args)
{
Thread[] thrs = new Thread[N];
for (int i = ; i < N; i++)
{
thrs[i] = new Thread(Counter);
thrs[i].Start();
}
for (int i = ; i < N; i++)
{
thrs[i].Join();
}
Console.WriteLine(iCnt); iCnt = ; ParameterizedThreadStart[] thrsp = new ParameterizedThreadStart[N];
object param = ;
for (int i = ; i < N; i++)
{
thrsp[i] = new ParameterizedThreadStart(ConterWithParam);
thrs[i] = new Thread(thrsp[i]);
thrs[i].Start(param);
}
for (int i = ; i < N; i++)
{
//当NewThread调用Join方法的时候,MainThread就被停止执行,直到NewThread线程执行完毕
thrs[i].Join();
}
Console.WriteLine(iCnt);
} static void Counter()
{
Thread.Sleep();
iCnt++;
//Console.WriteLine("finish iCnt++,now iCnt is " + iCnt);
} static void ConterWithParam(object param)
{
Thread.Sleep();
int i = (int)param;
iCnt += i;
//Console.WriteLine("finish iCnt+"+i+",now iCnt is " + iCnt);
}
该例子输出结果
2)互斥信号灯mutex
第一节的结果是不是有点奇怪。明明加了10000次,结果却是9550.
带参数的那个例子,一次加2,加10000次,应该是20000才对。结果却是19678.
这是因为对全局变量的访问iCnt出现了冲突。比如两个线程同时取到了iCnt=0时的值,同时执行了i++,那么iCnt的最后状态肯定是1,而不是会2。为了让iCnt得到正确的值。
我们引入互斥信号灯。
static int iCnt = ;
static readonly int N = ;
static Mutex mut = new Mutex(); static void Main(string[] args)
{
Thread[] thrs = new Thread[N];
for (int i = ; i < N; i++)
{
thrs[i] = new Thread(Counter);
thrs[i].Start();
}
for (int i = ; i < N; i++)
{
thrs[i].Join();
}
Console.WriteLine(iCnt); iCnt = ; ParameterizedThreadStart[] thrsp = new ParameterizedThreadStart[N];
object param = ;
for (int i = ; i < N; i++)
{
thrsp[i] = new ParameterizedThreadStart(ConterWithParam);
thrs[i] = new Thread(thrsp[i]);
thrs[i].Start(param);
}
for (int i = ; i < N; i++)
{
//当NewThread调用Join方法的时候,MainThread就被停止执行,直到NewThread线程执行完毕
thrs[i].Join();
}
Console.WriteLine(iCnt);
} static void Counter()
{
Thread.Sleep();
//锁
mut.WaitOne();
iCnt++;
//释放
mut.ReleaseMutex();
//Console.WriteLine("finish iCnt++,now iCnt is " + iCnt);
} static void ConterWithParam(object param)
{
Thread.Sleep();
//锁住
mut.WaitOne();
int i = (int)param;
iCnt += i;
//释放
mut.ReleaseMutex();
//Console.WriteLine("finish iCnt+"+i+",now iCnt is " + iCnt);
}
本次执行结果
3) 同步信号灯Semaphore
用最经典的生产者-消费者来解释。
static Semaphore sem = new Semaphore(, );
static Semaphore sem2 = new Semaphore(, ); static void Main(string[] args)
{
Console.WriteLine("消费者等生产者生产一个item");
Thread thConsumer = new Thread(Consume);
thConsumer.Start();
Thread thProductor = new Thread(Product);
thProductor.Start(); thConsumer.Join();
thProductor.Join();
Console.WriteLine("............................."); Console.WriteLine("多并发的例子.....");
for (int i = ; i < ; i++)
{
Thread t1 = new Thread(Consume2);
t1.Start();
Thread t2 = new Thread(Product2);
t2.Start();
}//end for } static void Product()
{
Thread.Sleep();
Console.WriteLine("Product an item...");
sem.Release();
} static void Consume()
{
Thread.Sleep();
Console.WriteLine("Consumer is waiting an item...");
sem.WaitOne();
Console.WriteLine("Consumer get an item...");
} static void Product2()
{
Thread.Sleep();
Console.WriteLine("Product an item...");
sem2.Release();
} static void Consume2()
{
Thread.Sleep();
Console.WriteLine("Consumer is waiting an item...");
sem2.WaitOne();
Console.WriteLine("Consumer get an item...");
}
C# 语言的多线程编程,完全是本科OS里的知识的更多相关文章
- Rust语言的多线程编程
我写这篇短文的时候,正值Rust1.0发布不久,严格来说这是一门兼具C语言的执行效率和Java的开发效率的强大语言,它的所有权机制竟然让你无法写出线程不安全的代码,它是一门可以用来写操作系统的系统级语 ...
- C语言 之 多线程编程
一.基础知识 计算机的核心是CPU,承担了所有的计算任务. 操作系统是计算机的管理者,负责任务的调度.资源的分配和管理,统领整个计算机硬件. 应用程序则是具有某种功能的程序,程序是运行于操作系统之上的 ...
- linux下c语言的多线程编程
我们在写linux的服务的时候,经常会用到linux的多线程技术以提高程序性能 多线程的一些小知识: 一个应用程序可以启动若干个线程. 线程(Lightweight Process,LWP),是程序执 ...
- java多线程编程(1) 线程的基本知识
在前面研究过多线程与进程的区别. 这里在稍微总结一下: 进程:程序动态的一次执行过程. 线程:可以只是程序员的一部分的执行过程 每个进程有多个线程组成,在java程序中,至少两个线程一个是垃圾回收线程 ...
- linux下C语言多线程编程实例
用一个实例.来学习linux下C语言多线程编程实例. 代码目的:通过创建两个线程来实现对一个数的递加.代码: //包含的头文件 #include <pthread.h> #include ...
- C语言中的多线程编程
很久很久以前,我对C语言的了解并不是很多,我最早听说多线程编程是用Java,其实C语言也有多线程编程,而且更为简单.方便.强大.下面就让我们简单领略一下Unix C语言环境下的多线程编程吧! 下面先看 ...
- C语言多线程编程
HANDLE CreateThread(LPSECURITY_ATTRIBUTES lpThreadAttributes, DWORD dwStackSize, LPTHREAD_START_ROUT ...
- C语言使用pthread多线程编程(windows系统)二
我们进行多线程编程,可以有多种选择,可以使用WindowsAPI,如果你在使用GTK,也可以使用GTK实现了的线程库,如果你想让你的程序有更多的移植性你最好是选择POSIX中的Pthread函数库,我 ...
- Linux C语言多线程编程实例解析
Linux系统下的多线程遵循POSIX线程接口,称为 pthread.编写Linux下的多线程程序,需要使用头文件pthread.h,连接时需要使用库libpthread.a.顺便说一下,Linux ...
随机推荐
- NSIS:简单按钮美化插件SkinButton,支持透明PNG图片。
原文 NSIS:简单按钮美化插件SkinButton,支持透明PNG图片. 征得作者贾可的同意,特发布按钮美化插件SkinButton. 插件说明: 使用GDI+库写的一个简单按钮美化插件,支持透明P ...
- Linux init详解(转)
Linux init详解 一.什么是INIT: init是Linux系统操作中不可缺少的程序之一. 所谓的init进程,它是一个由内核启动的用户级进程. 内核自行启动(已经被载入内存,开始运行,并已初 ...
- VS路宏 vc++于OutDir、ProjectDir、SolutionDir不同的路径
说明 $(RemoteMachine) 设置为"调试"属性页上"远程计算机"属性的值.有关很多其它信息,请參见更改用于 C/C++ 调试配置的项目设置. $(R ...
- 【SSH之旅】一步学习的步Struts1相框(三):分析控制Struts1示例
部分博客,,先后实施了Struts抽样.现在我们来分析这个样本.具体解释Struts1. Struts1的几个核心组件是值得我们注意的: (1)ActionServlet(核心控制器). (2)Act ...
- GMSK调制仿真
GMSK 调制的的原理非常简单. 就是MSK调制前进行Gauss滤波. 在实现中有这样的方法,首先产生高斯系数,对称的上升陂和下降陂系数.输入一个符号,进行上采样,经过高斯滤波器,滤波器的输出做有符号 ...
- nodejs使用connect-mongodb报错(Please ensure that you set the default write concern)
原本是使用connect-mongo的,可能是express版本号的升级报错了.改用connect-mongodb.可是使用后出现了例如以下的警告: G:\nodejs\moviesite>gr ...
- HDU 1505 Largest Rectangle in a Histogram && HDU 1506 City Game(动态规划)
1506意甲冠军:给你一个连续的直方图(拼贴底部长度1).求连续基质区. 对每一个直方图,分别向左向右进行扩展. #include<cstdio> #include<stdlib.h ...
- hdu2844 & poj1742 Coin ---多重背包--两种方法
意甲冠军:你有N种硬币,每个价格值A[i],每个号码C[i],要求. 在不超过M如果是,我们用这些硬币,有多少种付款的情况下,.那是,:1,2,3,4,5,....,M这么多的情况下,,你可以用你的硬 ...
- YUV422蓝色屏幕输出的调试援助
YUV422蓝色屏幕输出的调试援助 YUV422有YUYV,YVYU,UYVY,VYUY四种,以下笔者就就以UYVY为例介绍一下数据构成.因为常常要跟视频输入打交道,所以YUV422这种常见的视频信号 ...
- matlab配置Libsvm 防止备忘录
1 首先我们要下载一个Libsvm 工具箱 其中,这一切都可以被下载到 2 我们解包 我解压在桌面上 住址C:\Users\Administrator\Desktop\libsvm 3打开matlab ...