三种多线程方法的区别

三种多线程方法的区别

1、直接继承Thread类实现多线程:

//创建子类继承Thread类
class TickWindow extends Thread{
    
    
    private int tickets = 100;
    //重写Thread类中的run方法
    public void run(){
    
    
        while(true){
    
    
            if(tickets > 0){
    
    
                System.out.println(Thread.currentThread().getName()+"正在发售第 "+tickets--+" 张票");
            }
        }
    }
}
public class Example04 {
    
    
    public static void main(String[] args) {
    
    
        //创建4个线程对象TicketWindow并开启,来模拟4个售票窗口
        new TickWindow().start();
        new TickWindow().start();
        new TickWindow().start();
        new TickWindow().start();
    }
}

运行结果如下:
在这里插入图片描述
可以看出每张票都被发售了4次,和我们平时的售票逻辑是不符合的。出现这种情况的原因是4个线程没有共享这些票,而是每个独自拥有100张票。所以是每个线程独立处理各自的资源,而不是处理共享资源。

2、Runnable接口实现多线程(Callable接口实现也可以):

//定义一个实现Runnable接口的实现类
class TicketWindow2 implements Runnable{
    
    
    private int tickets = 100;
    @Override
    public void run() {
    
    
        while(true){
    
    
            if(tickets > 0){
    
    
                System.out.println(Thread.currentThread().getName()+"正在发售第 "+tickets--+" 张票");
            }
        }
    }
}
public class Example05 {
    
    
    public static void main(String[] args) {
    
    
        //创建ticketwindow实例对象
        TicketWindow2 ticketWindow2 = new TicketWindow2();
        new Thread(ticketWindow2,"window 1").start();
        new Thread(ticketWindow2,"window 2").start();
        new Thread(ticketWindow2,"window 3").start();
        new Thread(ticketWindow2,"window 4").start();
    }
}

运行结果如下:
在这里插入图片描述
在这个例子中,通过Runnable接口的方法只创建了一个TicketWindow2对象,然后创建了4个线程,每个线程都是调用同一个对象的run()方法,这样就确保了4个线程访问的是统一的资源内容,达到共享资源的目的。

优点:

1、适合多个线程处理一个共享资源的情况,将线程如代码、数据有效分离,充分体现了面向对象的设计思想。

2、避免java单继承特性所带来的局限性,因为一个类不能同时继承两个父类,所以在当前的类已经继承了一个父类的前提下,那么就只能采用实现Runnable接口的方法或者Callable接口的方法来实现多线程。

猜你喜欢

转载自blog.csdn.net/komed/article/details/114422713