多线程详细分析与介绍

本文介绍了Java中实现多线程的两种方法,并通过示例详细解释了如何使用这两种方法。此外,还探讨了多线程的安全问题及解决方案,并提供了一个使用synchronized关键字确保线程安全的售票系统案例。最后,通过一个具体的例子展示了线程间的同步通信。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >



Java中的多线程的已经学习了两三天,现在就将我学习的心得与体会以及我对多线程的理解与大家分享一下,本博文绝对原创,如有理解不对或与读者理解有相悖之处,请留言,我们一起讨论一下,共同进步。

 

传统的实现多线程的方法有两种:

1.      通过继承Thread,并重写run方法来实现

2.      通过实现runnable接口重写run方法来实现

下面举例说明两种实现方法:

Public class MyThread extends Thread

{

   Publicvoid run()

{

   //要实现的代码

}

}

 

Public class MyThread2 implements Runnable

{

  Publicvoid run()

{

   //实现代码

}

}

 

Public class ThreadTest

{

   Publicstatic void main(String[] args)

   {

     NewMyThread().start();

    MyThread2 thread=new MyThread2();

     NewThread(thread).start();

     NewThread(thread).start();

   }

}

 

通过上述代码,我们可以看出线程最基本的使用方法,同时我们也发现通过实现runnbale接口实现的线程。可以共享同一份数据,所以在编写多线程的程序是我们大多数还是会使用第二种方法的,第二种方法可以为我们带来很多意想不到的方便。

 

 

多线程的调用原理:

 

多线程的调用是CPU随机调用的,也就是说谁先得到cpu的资源谁先执行,如果一个线程开始执行,但是并不是得等到这个线程执行完以后别的线程才能调用,在上一个线程执行的过程期间,别的线程也会得到执行,只不过是多个线程一起争夺cpu,谁抢到谁执行,所以我们可以看到多个线程似乎是一起执行的。

 

 

多线程的安全问题:

安全问题要使用synchronized关键字,使用方法有synchronized块和synchronized方法,

Synchronized有一个锁(一个对象),当进入块或方法或锁变为0,其余用同一对象作为锁的方法不能被访问直到这个方法执行完。

 

下面给一个买票系统的例子:

package com.li;

 

public class ThreadSafe

{

 

    /**

     * @param args

     */

    static TrainTicket ticket=new TrainTicket();

    public static void main(String[] args)

    {

      

      

       new Thread(new Runnable()

       {

          

           @Override

           public void run()

           {

              while(true)

              {

                  ticket.ticketSale();

              }

             

             

           }

       }).start();

       new Thread(new Runnable()

       {

          

           @Override

           public void run()

           {

              while(true)

              {

                  ticket.ticketSale();

              }

             

             

           }

       }).start();

 

    }

   

    static class TrainTicket

    {

       int ticketNumber=100;

       public synchronized void  ticketSale()

       {

           if(ticketNumber>0)

           {

              ticketNumber--;

              System.out.println(Thread.currentThread().getName()+"sell"+ticketNumber);

           }

          

       }

      

    }

   

 

}

 

 

执行结果:

Thread-1sell99

Thread-1sell98

Thread-1sell97

Thread-1sell96

Thread-1sell95

Thread-1sell94

Thread-1sell93

Thread-1sell92

Thread-1sell91

Thread-1sell90

Thread-1sell89

Thread-1sell88

Thread-1sell87

Thread-1sell86

Thread-1sell85

Thread-1sell84

Thread-1sell83

Thread-1sell82

Thread-1sell81

Thread-1sell80

Thread-1sell79

Thread-1sell78

Thread-1sell77

Thread-1sell76

Thread-1sell75

Thread-1sell74

Thread-1sell73

Thread-1sell72

Thread-1sell71

Thread-1sell70

Thread-1sell69

Thread-1sell68

Thread-1sell67

Thread-1sell66

Thread-1sell65

Thread-1sell64

Thread-1sell63

Thread-1sell62

Thread-1sell61

Thread-1sell60

Thread-1sell59

Thread-1sell58

Thread-0sell57

Thread-0sell56

Thread-0sell55

Thread-0sell54

Thread-0sell53

Thread-0sell52

Thread-0sell51

Thread-0sell50

Thread-0sell49

Thread-0sell48

Thread-0sell47

Thread-0sell46

Thread-0sell45

Thread-0sell44

Thread-0sell43

Thread-0sell42

Thread-0sell41

Thread-0sell40

Thread-0sell39

Thread-1sell38

Thread-1sell37

Thread-1sell36

Thread-1sell35

Thread-1sell34

Thread-1sell33

Thread-1sell32

Thread-1sell31

Thread-1sell30

Thread-1sell29

Thread-1sell28

Thread-1sell27

Thread-1sell26

Thread-1sell25

Thread-1sell24

Thread-1sell23

Thread-1sell22

Thread-1sell21

Thread-1sell20

Thread-1sell19

Thread-1sell18

Thread-1sell17

Thread-1sell16

Thread-1sell15

Thread-1sell14

Thread-1sell13

Thread-1sell12

Thread-1sell11

Thread-1sell10

Thread-1sell9

Thread-1sell8

Thread-1sell7

Thread-1sell6

Thread-1sell5

Thread-1sell4

Thread-1sell3

Thread-1sell2

Thread-1sell1

Thread-1sell0

 

 

最后介绍一下线程之间的同步通信问题:

通常会用wait和notify方法

当遇到wait是线程会阻塞,直到遇到同一对象调用的notify方法

 

下面给出一个实例:

 

这个例子实现输出一个对象后,等待放入另一个对象后再输出,如此往复

 

package com.li.example;

 

 

 

/**

此程序实现了线程的同步,考虑到了线程的安全性问题,同时还利用wait()和notify()实现了线程之间的通信问题,

线程的运行机制,虽然启动了一个线程,但不是要完全等待一个线程执行完才执行另外一个线程,而是cpu动态的分配,可能一个线程

正在运行,但cpu将资源分配给了另外一个线程,这就有肯能造成线程的安全性问题,安全性问题可以用synchronized解决

 

 */

class Q {

    private String name = "unknown";

    private String sex = "unknown";

    private boolean qFull = false;

 

    public synchronized void set(String name, String sex) {

       if (qFull)

           try {

              wait();

           }catch(InterruptedException e1) {

              // TODO Auto-generated catch block

              e1.printStackTrace();

           }

       this.name = name;

       try {

           Thread.sleep(20);

       }catch(Exception e) {

       }

       this.sex = sex;

       qFull = true;

       notify();

 

    }

 

    public synchronized void get() {

 

       if (!qFull)

           try {

              wait();

           }catch(InterruptedException e) {

              // TODO Auto-generated catch block

              e.printStackTrace();

           }

 

       System.out.println(name);

       System.out.println(sex);

 

       qFull = false;

 

       notify();

 

    }

 

}

 

class Producer implements Runnable {

    Qq = new Q();

 

    public Producer(Q q) {

       this.q = q;

    }

 

    int i = 0;

 

    public void run() {

       while (true) {

           if (i == 0)

              q.set("li si","female");

           else

              q.set("zhang san","male");

           i = (i + 1) % 2;

       }

    }

}

 

class Consumer implements Runnable {

    Qq = new Q();

 

    public Consumer(Q q) {

       this.q = q;

    }

 

    public void run() {

       while (true) {

           q.get();

 

       }

    }

}

 

class ThreadDemo2 {

    static Q q = new Q();

 

    public static void main(String[] args) {

       new Thread(new Producer(q)).start();

       new Thread(new Consumer(q)).start();

    }

}

 





评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值