并发应用程序中可能出现的问题

数据竞争

如果有两个或者多个任务在临界段之外对一个共享变量进行写入操作,也就是说没有使用任何同步机制,那么应用程序可能存在数据竞争(也叫作竞争条件)。

在这些情况下,应用程序的最终结果可能取决于任务的执行顺序。

死锁

当两个(或多个)任务正在等待必须由另一线程释放的某个共享资源,而该线程又正在等待必须由前述任务之一释放的另一共享资源时,并发应用程序就出现了死锁。

当系统中同时出现如下四种条件时,就会导致这种情形。我们将其称为 Coffman 条件。

有一些机制可以用来避免死锁:

活锁

如果系统中有两个任务,它们总是因对方的行为而改变自己的状态,那么就出现了活锁。
最终结果是它们陷入了状态变更的循环而无法继续向下执行。

例如,有两个任务:任务 1 和任务 2,它们都需要用到两个资源:资源 1 和资源 2。
假设任务 1 对资源 1 加了一个锁,而任务 2对资源 2加了一个锁。
当它们无法访问所需的资源时,就会释放自己的资源并且重新开始循环。
这种情况可以无限地持续下去,所以这两个任务都不会结束自己的执行过程。

资源不足

当某个任务在系统中无法获取维持其继续执行所需的资源时,就会出现资源不足。

当有多个任务在等待某一资源且该资源被释放时,系统需要选择下一个可以使用该资源的任务。
如果你的系统中没有设计良好的算法,那么系统中有些线程很可能要为获取该资源而等待很长时间。

要解决这一问题就要确保公平原则。 所有等待某一资源的任务必须在某一给定时间之内占有该资源。
可选方案之一就是实现一个算法,在选择下一个将占有某一资源的任务时,对任务已等待该资源的时间因素加以考虑。

然而,实现锁的公平需要增加额外的开销,这可能会降低程序的吞吐量。

优先权反转

当一个低优先权的任务持有了一个高优先级任务所需的资源时,就会发生优先权反转。
这样的话,低优先权的任务就会在高优先权的任务之前执行。