一个竞态条件是一个特殊的条件,可能发生在一个临界部分的内部(critical section)。一个临界部分是一段正在被多线程执行的代码,以及线程执行的顺序对于临界部分并发执行的结果产生影响。
当多线程执行一个临界段的结果依赖线程执行的顺序可能是不同的,这个临界段包含一个竞态条件。这个竞态条件的词条源于这个线程正在竞速通过这个临界段的暗喻,并且这个竞争的结果影响着执行这个临界段的结果。
这个可能听起来有点复杂,以至于我将会在下面的部分详细阐述关于竞态条件和临界段。
临界段(Critical Sections)
在相同的应用内部运行不止一个线程不会被他自己引起问题。当多个线程访问相同的资源问题就会出现。例如相同的内存(变量,数组,或者对象),系统(数据库,web服务)或者文件。
事实上,如果一个或者多个线程写这些资源的时候问题会出现。让多个线程读取相同的资源是安全的,只要资源不会改变。
这里有一个例子,如果多个线程同事执行可能会失败:
public class Counter { protected long count = 0; public void add(long value){ this.count = this.count + value; } }
this.count = 0; A: Reads this.count into a register (0) B: Reads this.count into a register (0) B: Adds value 2 to register B: Writes register value (2) back to memory. this.count now equals 2 A: Adds value 3 to register A: Writes register value (3) back to memory. this.count now equals 3
public class TwoSums { private int sum1 = 0; private int sum2 = 0; public void add(int val1, int val2){ synchronized(this){ this.sum1 += val1; this.sum2 += val2; } } }
public class TwoSums { private int sum1 = 0; private int sum2 = 0; public void add(int val1, int val2){ synchronized(this){ this.sum1 += val1; } synchronized(this){ this.sum2 += val2; } } }
翻译地址:http://tutorials.jenkov.com/java-concurrency/race-conditions-and-critical-sections.html