同步代码块
Java虚拟机为每个对象配备一把锁和一个等候集,这个对象可以是实例对象,也可以是类对象。对实例对象进行加锁可以保证与这个类相关联的线程可以通过互斥地使用类对象的锁。
一个类的静态成员方法变量和静态成员方法隶属于类对象,而一个类的非静态成员变量和非静态成员方法属于类的实例对象。
在方法中,用Synchronized声明的语句块称为同步代码块
synchronized(synObject)
{
}
关键代码块:必须获得对象synObiect的锁才能执行,当一个线程想要进入 该对象的关键代码时,JVM将检查该对象的锁是否被其他线程获得,如果没有,则JVM把该对象的锁交给当前请求锁的线程,该线程获得锁后即可进入关键代码区域。
多个线程执行的不确定性引起执行结果的不稳定 多个线程对账本的共享,会造成操作的不完整性,会破坏数据。
public class CreditCard {
public static void main(String[] args) {
User u = new User("张三", 100000);
UserThread t1 = new UserThread("线程A", u, 200);
UserThread t2 = new UserThread("线程B", u, -600);
UserThread t3 = new UserThread("线程C", u, -800);
UserThread t4 = new UserThread("线程D", u, -300);
UserThread t5 = new UserThread("线程E", u, 1000);
UserThread t6 = new UserThread("线程F", u, 200);
t1.start();
t2.start();
t3.start();
t4.start();
t5.start();
t6.start();
}
}
class UserThread extends Thread{
private User u;
private int y = 0;
UserThread(String name, User u,int y){
super(name);
this.u = u;
this.y = y;
}
public void run(){
u.oper(y);
}
}
class User{
private String code;
private int cash;
User(String code,int cash) {
this.code = code;
this.cash = cash;
}
public String getCode(){
return code;
}
public void setCode(String code ){
this.code = code;
}
public void oper(int x){
try{
Thread.sleep(10);
synchronized (this){
this.cash +=x;
System.out.println(Thread.currentThread().getName()+ "运行结束,增加" + x +",当前账户余额为:" + cash);
}
Thread.sleep(10);
}catch (InterruptedException e){
e.printStackTrace();
}
}
public String toString(){
return "User{" + "code = '" + code + '\'' + ", cash=" + + cash + '}';
}
}
|