zoukankan      html  css  js  c++  java
  • 关于多线程中synchronized的使用位置

    在练习多线程之售票的时候,对于synchronized的使用有些困惑,因为我是用以下代码:

    public class ThreadDemo5 {
    
    	/**
    	 * @param args
    	 */
    	public static void main(String[] args) {
    		// TODO Auto-generated method stub
    		saleTicket_5 st = new saleTicket_5();
    		Thread t1 = new Thread(st);
    		Thread t2 = new Thread(st);
    		Thread t3 = new Thread(st);
    		Thread t4 = new Thread(st);
    		t1.start();
    		t2.start();
    		t3.start();
    		t4.start();
    	}
    
    }
    
    class saleTicket_5 implements Runnable {
    	private int ticket = 1000;
    	Object obj = new Object();
    
    	public void run() {
    		synchronized (obj) {
    
    			while (ticket > 0) {
    				try {
    					Thread.sleep(1000);
    				} catch (InterruptedException e) {
    					// TODO Auto-generated catch block
    					e.printStackTrace();
    				}
    				System.out.println(Thread.currentThread().getName() + "****"
    						+ ticket--);
    			}
    		}
    	}
    }
    

    synchronized在此虽然将共享资源的代码块上锁,但是synchronized上锁之后,线程需要把synchronized里面的代码块执行完毕后才能释放锁,此代码块里面是一个循环,这就造成了最后的结果只有Thread-0线程在执行的情况。


    之后对其进行修改:

    public class ThreadDemo5 {
    
    	/**
    	 * @param args
    	 */
    	public static void main(String[] args) {
    		// TODO Auto-generated method stub
    		saleTicket_5 st = new saleTicket_5();
    		Thread t1 = new Thread(st);
    		Thread t2 = new Thread(st);
    		Thread t3 = new Thread(st);
    		Thread t4 = new Thread(st);
    		t1.start();
    		t2.start();
    		t3.start();
    		t4.start();
    	}
    
    }
    
    class saleTicket_5 implements Runnable {
    	private int ticket = 1000;
    	Object obj = new Object();
    
    	public void run() {
    
    		while (true) {
    			synchronized (obj) {
    				if (ticket > 0) {
    
    					try {
    						Thread.sleep(10);
    					} catch (InterruptedException e) {
    						// TODO Auto-generated catch block
    						e.printStackTrace();
    					}
    					System.out.println(Thread.currentThread().getName()
    							+ "****" + ticket--);
    				} else
    					break;
    			}
    
    		}
    	}
    }
    

    需要注意的是synchronized里面需要包含全部的共享资源,以保证对共享资源操作的原子性,另外 不要忘记退出while循环

  • 相关阅读:
    C#数组的使用
    CLR设计类型之接口
    CLR类型设计之泛型(二)
    CLR类型设计之泛型(一)
    CLR类型设计之属性
    CLR类型设计之参数传递
    CLR类型设计之方法与构造器
    将博客搬至CSDN
    Unity_与android交互
    CSS3制作hover下划线动画
  • 原文地址:https://www.cnblogs.com/JSD1207ZX/p/9386230.html
Copyright © 2011-2022 走看看