/**
* Created by gmy on 2017/10/14.
*/
public class App {
public static void main(String[] args) throws InterruptedException {
final Runner runner=new Runner();
Thread t1=new Thread(new Runnable() {
@Override
public void run() {
try {
runner.firstThread();
} catch (InterruptedException e) {
e.printStackTrace();
}
}
});
Thread t2 =new Thread(new Runnable() {
@Override
public void run() {
try {
runner.secondThread();
}catch (InterruptedException ignored){
}
}
});
t1.start();
t2.start();
t1.join();
t2.join();
runner.finished();
}
}
/**
* Created by gmy on 2017/10/14.
*/
public class Runner {
private Account account1=new Account();
private Account account2=new Account();
private Lock lock1=new ReentrantLock();
private Lock lock2=new ReentrantLock();
private void acquireLocks(Lock firstLock,Lock secondLock) throws InterruptedException{
while(true){
boolean gotFirstLock=false;
boolean gotSecondLock=false;
try {
gotFirstLock=firstLock.tryLock();//tryLock是看这个锁是否是可用的,没有被其他线程占用
gotSecondLock=secondLock.tryLock();
}finally {
if(gotFirstLock&&gotSecondLock)return;
else if (gotFirstLock)firstLock.unlock();
else if (gotSecondLock)secondLock.unlock();
}
Thread.sleep(1);
}
}
public void firstThread()throws InterruptedException{
Random random=new Random();
for (int i=0;i<10000;i++){
acquireLocks(lock1,lock2);
try {
Account.transfer(account1,account2,random.nextInt(100));
}finally {
lock1.unlock();
lock2.unlock();
}
}
}
public void secondThread()throws InterruptedException{
Random random=new Random();
for (int i=0;i<10000;i++){
acquireLocks(lock2,lock1);
try {
Account.transfer(account2,account1,random.nextInt(100));
}finally {
lock1.unlock();
lock2.unlock();
}
}
}
public void finished(){
System.out.println("Account 1 balance "+account1.getBalance());
System.out.println("Account 2 balance "+account2.getBalance());
System.out.println("Total balance"+(account2.getBalance()+account1.getBalance()));
}
}
public class Account {
private int balance=10000;//底金
public void deposit(int amount){//存钱
balance+=amount;
}
public void withdraw(int amount){//取钱
balance-=amount;
}
public int getBalance(){
return balance;
}
public static void transfer(Account account1,Account account2,int amount){//转账
account1.withdraw(amount);
account2.deposit(amount);
}
}
解析:
- thread.Join把指定的线程加入到当前线程。例如在main 线程中调用了t1.join()是指t1线程执行完毕