windows多线程编程,为什么需要多线程编程

多线程编程的难度是很大的。这是由于多线程程序的问题无法用测试进行检验。唯一的办法是通过逻辑评审。这里我来分享一下评审多线程程序时使用的思路。

交互逻辑

先说说理论。多线程程序评审有两个指标:

  • 安全性 共有资源在任何时刻最多只有一个线程使用。
  • 生存性 所有线程最终都能占有共有资源,没有死锁。

这里所说的共有资源可以是变量,也可以是一段代码。为了说明线程控制的基本原则,本文的例子没有使用编程语言中的多线程控制指令。现在举例,有很多线程每个线程中都有一个数,你想计算出这些数的合计。用伪代码表示:

  1. number =from_thread;
  2. summary+=number;

这里共有资源有两个number和summary,我们假定有两个线程,一个在执行第1行,另一个在执行第2行,由于没有任何限制,这种情况有可能发生,线程不安全。后果是可能漏掉一些数。为了确保安全,考虑建立一个标示,如果标示为零就把标示加一并执行累计,否则,就等待到标示为零。累计完毕后将标示设为零。伪代码:

  1. while(flag!=0){wait();};
  2. flag++;
  3. number =from_thread;
  4. summary+=number;
  5. flag=0;

检验安全性,假定有两个线程,一个在执行第2行,另一个在执行第3行,我们发现只有flag为零第二个线程才能执行第二行。第一个线程在第三行的时候,flag必不为零。线程是安全的。

接下来检验生存性,假定有线程在第1行等待,而flag为零,这个情况不会出现。因此,可生存。

5个哲学家就餐

这是一个十分经典的多线程问题,网上有很多雷同的答案,大部分都是错的。当年也曾困扰微软的工程师,他们使用了随机的GUID解决了。但理论上说这个方法并不完美,如果出现了相同的GUID线程就不安全了。虽然概率微乎其微,但毕竟不是零。而Linux也找到了彻底的解法,完美地保证了线程安全。说来话长。限于篇幅,就说这么多吧,如有疑问还请包涵。

生活中的例子

交互逻辑并不只存在在编程领域,它和我们的生活息息相关。举个例子,法律规定遗产继承要由直系亲属平均分配。其实,这是不安全的。我们用这样一个家庭进行分析,父母夫妻子共五个人,夫与子出去旅行遭遇空难双双死亡。由于无法弄清楚夫与子的死亡顺序(两个线程),夫的遗产(共有资源)继承上出现了纠纷,若夫先亡,剩下4人每人继承1/4,子再亡,妻可再继承子的1/4.共计1/2财产。若子先亡,无财产继承,夫再亡,剩下三人每人1/3。

因为你已经会使用多线程了,如果是要熟悉多线程编程,你可以检查你是否熟悉这几点:

检查表

1、线程的内存(内核态和用户态)消耗,这个对于你使用的语言是否有虚拟机运行时是不一样的。同时需要了解进程的内存布局。

2、线程的调度/切换代价、系统调用机制的实现。

3、线程池的设计(是真的设计)和使用。

4、多线程的同步策略,多种级别锁的实现和性能评估,死锁问题。轻量锁或无锁模式的实现。熟悉常用三方组件提供的接口中的原子操作,自定义分布式锁的实现。

5、熟悉异步IO、IO复用的详细机制和使用。我们平时碰到的大部分应用都是IO密集型的,多线程此时和IO是密不可分的。

6、识别多线程环境(包括隐蔽的多进程协作),能对多线程环境出现的同步和性能问题做出分析和给出解决方案。

语言平台

如果你需要做基于客户端的编程,需要了解应用程序模型关于UI线程的设计。

同时基于你使用的语言平台,你还需要了解相关的基于并行任务编程以及语言本身提供的线程和同步接口,async/await编程模式,并行库使用等。

我觉得仅仅是熟悉多线程编程,以上应该就差不多了。另外,不同公司在招聘要求中的描述的“熟悉”可能内涵不太一样,不过你如果上面的检查表过关了,相信大部分公司都能过这一关。

本文来自用户投稿,不代表【51考个证】立场,如若转载,请注明出处:https://www.51kgz.cn/32603.html

发表评论

登录后才能评论

评论列表(0条)