线程并发问题卖票Demo

Posted java-jiangtao-home

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了线程并发问题卖票Demo相关的知识,希望对你有一定的参考价值。

 1 package buyTiket;
 2 
 3 public class SaleTicket extends Thread{
 4     private String name;
 5     
 6     
 7     
 8     
 9     public SaleTicket(String name) {
10         super(name);
11     
12     }
13 
14     private static int tickets = 100;
15     private static Object obj = new Object();
16     private static B a = new B();
17     @Override
18     public void run() {
19     
20         
21         while(true) {
22             /**
23              * synchronized同步代码块的锁对象可以是任意类对象(线程的实现方式是继承于Thread)
24              * 这个类对象必须是线程共享的
25              */
26             
27             
28             synchronized (a) {
29                 if(tickets>0) {
30                     try {
31                         Thread.sleep(50);
32                     } catch (InterruptedException e) {
33                         // TODO Auto-generated catch block
34                         e.printStackTrace();
35                     }
36                     
37                     
38                     System.out.println(this.getName()+"正在卖"+tickets--+"张票");
39                 }else {
40                     System.out.println("票已经售完");
41                     break;
42                 }
43             }
44             
45             
46             
47         }
48     }
49 }
50 class A{
51     
52     
53 }
 1 package buyTiket;
 2 
 3 public class TicketTest {
 4     
 5     public static void main(String[] args) {
 6         SaleTicket st1 = new SaleTicket("窗口1");
 7         SaleTicket st2 = new SaleTicket("窗口2");
 8         SaleTicket st3 = new SaleTicket("窗口3");
 9         SaleTicket st4 = new SaleTicket("窗口4");
10         /**
11          * 针对线程的安全性问题:我们需要使用同步(就是要加锁,共享资源只能一个人访问)锁。
12          * synchronized(锁对象){
13          *     //操作共享资源的代码
14          * }
15          * 
16          * 同步代码加在什么地方?
17          * 1.代码被多个线程访问
18          * 2.代码中有共享的数据
19          * 3共享数据被多条语句操作
20          */
21         st1.start();
22         st2.start();
23         st3.start();
24         st4.start();
25     }
26 
27 }
package buyTiket;

public class SaleTicket2 extends Thread{
    private String name;
    
    
    
    
    public SaleTicket2(String name) {
        super(name);
    
    }

    private static int tickets = 100;
    private static Object obj = new Object();
    private static A a = new A();
    @Override
    public void run() {
    
        
        while(true) {
            /**
             * synchronized同步代码块的锁对象可以是任意类对象(线程的实现方式是继承于Thread)
             * 这个类对象必须是线程共享的
             */
            int i=0;
            if(i%2==0) {
                synchronized (a) {
                    if(tickets>0) {
                        try {
                            Thread.sleep(0);
                        } catch (InterruptedException e) {
                            // TODO Auto-generated catch block
                            e.printStackTrace();
                        }
                        
                        
                        System.out.println(this.getName()+"正在卖"+tickets--+"张票");
                    }else {
                        System.out.println("票已经售完");
                        break;
                    }
                }
            }
            else {
            synchronized (a) {
                if(tickets>0) {
                    try {
                        Thread.sleep(0);
                    } catch (InterruptedException e) {
                        // TODO Auto-generated catch block
                        e.printStackTrace();
                    }
                    
                    
                    System.out.println(this.getName()+"正在卖"+tickets--+"张票");
                }else {
                    System.out.println("票已经售完");
                    break;
                }
            }
            
            }
            i++;
            
        }
    }
}
class B{
    
    
}
 1 package buyTiket;
 2 
 3 public class TicketTest2 {
 4     
 5     public static void main(String[] args) {
 6         SaleTicket2 st1 = new SaleTicket2("窗口1");
 7         SaleTicket2 st2 = new SaleTicket2("窗口2");
 8         SaleTicket2 st3 = new SaleTicket2("窗口3");
 9         SaleTicket2 st4 = new SaleTicket2("窗口4");
10         /**
11          * 针对线程的安全性问题:我们需要使用同步(就是要加锁,共享资源只能一个人访问)锁。
12          * synchronized(锁对象){
13          *     //操作共享资源的代码
14          * }
15          * 
16          * 同步代码加在什么地方?
17          * 1.代码被多个线程访问
18          * 2.代码中有共享的数据
19          * 3共享数据被多条语句操作
20          */
21         st1.start();
22         st2.start();
23         st3.start();
24         st4.start();
25     }
26 
27 }
package buyTiket;

public class SaleTicket3 extends Thread{
    private String name;
    
    
    
    
    public SaleTicket3(String name) {
        super(name);
    
    }

    private static int tickets = 100;
    private static Object obj = new Object();
    private static A a = new A();
    @Override
    public void run() {
    
        
        while(true) {
            /**
             * synchronized同步代码块的锁对象可以是任意类对象(线程的实现方式是继承于Thread)
             * 这个类对象必须是线程共享的
             */
            int i=0;
            if(i%2==0) {
                //同步代码块
                /**
                 * 这个就是当前类的类synchronizedSaleTicket3.java
                 */
                synchronized (SaleTicket3.class) {
                    if(tickets>0) {
                        try {
                            Thread.sleep(0);
                        } catch (InterruptedException e) {
                            // TODO Auto-generated catch block
                            e.printStackTrace();
                        }
                        
                        
                        System.out.println(Thread.currentThread().getName()+"正在卖"+tickets--+"张票");
                    }else {
                        System.out.println("票已经售完");
                        break;
                    }
                }
            }
            else {
                saleTicked();
            
            }
            i++;
            
        }
    }
    /**
     * 静态方法的synchronized锁是当前类的类对象
     */
    public synchronized static void saleTicked() {
        
            if(tickets>0) {
                try {
                    Thread.sleep(0);
                } catch (InterruptedException e) {
                    // TODO Auto-generated catch block
                    e.printStackTrace();
                }
                
                
                System.out.println(Thread.currentThread().getName()+"正在卖"+tickets--+"张票");
            }else {
                System.out.println("票已经售完");
                
            }
        
        
        
        
    }
    
}
package buyTiket;

public class TicketTest3 {
    
    public static void main(String[] args) {
        SaleTicket3 st1 = new SaleTicket3("窗口1");
        SaleTicket3 st2 = new SaleTicket3("窗口2");
        SaleTicket3 st3 = new SaleTicket3("窗口3");
        SaleTicket3 st4 = new SaleTicket3("窗口4");
        /**
         * 针对线程的安全性问题:我们需要使用同步(就是要加锁,共享资源只能一个人访问)锁。
         * synchronized(锁对象){
         *     //操作共享资源的代码
         * }
         * 
         * 同步代码加在什么地方?
         * 1.代码被多个线程访问
         * 2.代码中有共享的数据
         * 3共享数据被多条语句操作
         */
        st1.start();
        st2.start();
        st3.start();
        st4.start();
    }

}
package buyTiket;

public class SaleTicket4 implements Runnable{

//    private Object obj = new Object();
    private int tickets = 100;
    @Override
    public void run() {
    
        
        while(true) {
            
            int i=0;
            if(i%2==0) {
                //同步代码块
                /**
                 * 非静态的锁就是当前的对象,它的锁是this
                 */
                synchronized (this) {
                    if(tickets>0) {
                        try {
                            Thread.sleep(0);
                        } catch (InterruptedException e) {
                            // TODO Auto-generated catch block
                            e.printStackTrace();
                        }
                        
                        
                        System.out.println(Thread.currentThread().getName()+"正在卖"+tickets--+"张票");
                    }else {
                        System.out.println("票已经售完");
                        break;
                    }
                }
            }
            else {
                saleTicked();
            }
            i++;
            
        }
    }
    /**
     * 非静态方法的synchronized锁是当前类的类对象
     */
    public synchronized void saleTicked() {
        
            if(tickets>0) {
                try {
                    Thread.sleep(0);
                } catch (InterruptedException e) {
                    // TODO Auto-generated catch block
                    e.printStackTrace();
                }
                
                
                System.out.println(Thread.currentThread().getName()+"正在卖"+tickets--+"张票");
            }else {
                System.out.println("票已经售完");
                
            }
        
        
        
        
    }
    
}
package buyTiket;

public class TicketTest4 {
    
    public static void main(String[] args) {
        SaleTicket4 st1 = new SaleTicket4();
        Thread t1 = new Thread(st1,"窗口1");
        SaleTicket4 st2 = new SaleTicket4();
        Thread t2 = new Thread(st1,"窗口2");
        SaleTicket4 st3 = new SaleTicket4();
        Thread t3 = new Thread(st1,"窗口3");
        SaleTicket4 st4 = new SaleTicket4();
        Thread t4 = new Thread(st1,"窗口4");
        
        
        t1.start();
        t2.start();
        t3.start();
        t4.start();
    }

}

 

以上是关于线程并发问题卖票Demo的主要内容,如果未能解决你的问题,请参考以下文章

多线程(多窗口卖票例子)

实现多线程的两种方式,卖票场景,亲测可用

实验11——java线程模拟卖票

Thread线程并发解决synchronized

Java线程安全问题代码实现

多线程卖票代码