one common way is if you have nested locks that aren't acquired in the same order. Thread 1 could acquire lock A and thread 2 could acquire lock B and they would deadlock.
var a = new object();
var b = new object();
lock(a) {
lock(b) {
}
}
// other thread
lock (b) {
lock(a) {
}
}
edit: non-lock example .. using waithandles. Suppose Socrates and Descartes are having steaks and they both, being well-mannered philosophers, require both a fork and a knife in order to eat. However, they have only one set of silverware, so it is possible for each to grab one utensil and then wait forever for the other to hand over their utensil.
See the Dining Philosopher's Problem
WaitHandle fork = new AutoResetEvent(), knife = new AutoResetEvent();
while(Socrates.IsHungry) {
fork.WaitOne();
knife.WaitOne();
Eat();
fork.Set();
knife.Set();
}
// other thread
while(Descartes.IsHungry) {
knife.WaitOne();
fork.WaitOne();
Eat();
knife.Set();
fork.Set();
}
与恶龙缠斗过久,自身亦成为恶龙;凝视深渊过久,深渊将回以凝视…