packagesynh;
/*classThreadDemoimplementsRunnable{
inttickets=100;//票数
Stringstr=newString("");
publicvoidrun(){
while(true){
/*
*分析synchronized方法
*synchronized代码块中的语句只能有一个线程在执行
*
*任意一个对象都有一个标志位,有1和0两种状态
*当程序执行到synchronized代码块的时候线程会检查对象的标志位是1还是0
*如果是1则执行程序,同是将对象的标志位设置为0,其他线程执行到synchronized代码块时一看对象标志位为0
*则线程会阻塞,一直等到对象的标志位为1再执行下面的程序
*本程序中一共产生了4个线程,当一个线程执行synchronized代码块的时候其他三个线程会发生阻塞
*第一个线程执行完synchronized代码块后会把对象的标志位设置为1,其他的三个线程中的其中一个
*会抢到synchronized代码块的执行权,同时会把对象的标志位设置为0,就以这样的顺序循环执行
*
*我们也可以把对象标志位看成一个监视器,当一个线程执行到synchronized代码块的时候会检查监视器的
*状态,一个刚执行完synchronized代码块的线程也可以再次检查监视器并执行synchronized代码块
*
*多个线程要实现同步,必须使用相同的监视器对象(本例中4个线程都是用的str同一个对象),
*如果多个线程使用的不是同一个监视器对象则达不到同步的效果
*
synchronized(str){
if(tickets>0){
try{Thread.sleep(1);}catch(Exceptione){}
System.out.println(Thread.currentThread().getName()+"issallingticket---"+tickets--);
}
}
}
}
}*/
classThreadDemoimplementsRunnable{
inttickets=100;//票数
Stringstr=newString("");
//在一个方法里实现同步
publicvoidrun(){
while(true){
sale();
}
}
/*
*同步方法和同步块道理一样,这里就不再说了
*当一个线程执行同步方法的时候其他的方法也不能再执行同步方法中的语句
*/
publicsynchronizedvoidsale(){
if(tickets>0){
try{Thread.sleep(1);}catch(Exceptione){}//模拟不同步的实现
System.out.println(Thread.currentThread().getName()+"issallingticket---"+tickets--);
}
}
}
classThreadTest{
publicstaticvoidmain(String[]args){
ThreadDemotd=newThreadDemo();
/*
*生成4个线程
*
*/
newThread(td).start();
newThread(td).start();
newThread(td).start();
newThread(td).start();
}
}
看完了线程间的同步,再看看同步方法和同步代码块之间的同步
packagesynch;
classThreadDemoimplementsRunnable{
inttickets=100;//票数
Stringstr=newString("");
//在一个方法里实现同步
publicvoidrun(){
if(str.equals("method")){
while(true){
sale();
}
}
else{
while(true){
synchronized(this){
if(tickets>0){
try{Thread.sleep(1);}catch(Exceptione){}
System.out.println(Thread.currentThread().getName()+"issallingticket---"+tickets--);
}
}
}
}
}
/*
*同步方法和同步块道理一样,这里就不再说了
*当一个线程执行同步方法的时候其他的方法也不能再执行同步方法中的语句
*/
publicsynchronizedvoidsale(){
if(tickets>0){
try{Thread.sleep(1);}catch(Exceptione){}//模拟不同步的实现
System.out.println("method:"+Thread.currentThread().getName()+"issallingticket---"+tickets--);
}
}
}
classThreadTest1{
publicstaticvoidmain(String[]args){
ThreadDemotd=newThreadDemo();
/*
*生成4个线程
*
*/
newThread(td).start();
//这里写这个sleep()是为了让CPU转到当前线程来执行
try{Thread.sleep(1);}catch(Exceptione){} td.str="method";
newThread(td).start();
//newThread(td).start();
//newThread(td).start();
}
}
这里最关键的一点就是要想让同步方法和同步代码块同步,两者就要使用相同的监视器对象
本程序中用的同一个监视器对象是this