:) 很简单的一个日常生活中的列子,一个账户给两个人用,每人都去取出这个账户的所有余额,如果一个线程取钱的操作刚好在账户余额减少之前就暂停,另外一个线程进入这个取钱的方法进行取钱,那么也就使这个账户的余额为负了
看如下的例子[code=java]public class Account
{
//封装账户编号、账户余额两个属性
private String accountNo;
private double balance;
public Account(){}
//构造器
public Account(String accountNo , double balance)
{
this.accountNo = accountNo;
this.balance = balance;
}
public void setAccountNo(String accountNo)
{
this.accountNo = accountNo;
}
public String getAccountNo()
{
return this.accountNo;
}
public void setBalance(double balance)
{
this.balance = balance;
}
public double getBalance()
{
return this.balance;
}
//下面两个方法根据accountNo来计算Account的hashCode和判断equals
public int hashCode()
{
return accountNo.hashCode();
}
public boolean equals(Object obj)
{
if (obj != null
&& obj.getClass() == Account.class)
{
Account target = (Account)obj;
return target.getAccountNo().equals(accountNo);
}
return false;
}
}[/code][code=java]public class DrawThread extends Thread
{
//模拟用户账户
private Account account;
//当前取钱线程所希望取的钱数
private double drawAmount;
public DrawThread(String name , Account account ,
double drawAmount)
{
super(name);
this.account = account;
this.drawAmount = drawAmount;
}
//当多条线程修改同一个共享数据时,将涉及到数据安全问题。
public void run()
{
//账户余额大于取钱数目
if (account.getBalance() >= drawAmount)
{
//吐出钞票
System.out.println(getName() +
"取钱成功!吐出钞票:" + drawAmount);
/*
try
{
Thread.sleep(1);
}
catch (InterruptedException ex)
{
ex.printStackTrace();
}
*/
//修改余额
account.setBalance(account.getBalance() - drawAmount);
System.out.println("\t余额为: " + account.getBalance());
}
else
{
System.out.println(getName() + "取钱失败!余额不足!");
}
}
}[/code][code=java]public class TestDraw
{
public static void main(String[] args)
{
//创建一个账户
Account acct = new Account("1234567" , 1000);
//模拟两个线程对同一个账户取钱
new DrawThread("甲" , acct , 800).start();
new DrawThread("乙" , acct , 800).start();
}
}[/code]这个例子运行结果之后就得出账户余额最后为负值, |