zoukankan      html  css  js  c++  java
  • 初识多线程之基础知识与常用方法

    1.线程与进程的描述:

     1.1进程:每个进程都有独立的代码和数据空间(进程上下文),进程间的切换会有较大的开销,一个进程包含1~n个线程。(进程是资源分配的最小单位)
      

    1.2线程:同一类线程共享代码和数据空间,每个线程有独立的运行栈和程序计数器(PC),线程切换开销小。(线程是cpu调度的最小单位)

    2.实现多线程的常用方式:

    继承Thread类    extends Thread

      实现Runnable接口  implements Runnable

       内部匿名类   

    Thread t = new Thread(new Runnable() {    
    });

    3.实现多线程的常用方式:

    推荐使用Runnable接口:原因有二:1 Java中的类仅仅只支持单继承,而接口支持多继承
                                    2 使用Runnable接口可以轻松的实现多个线程间的资源共享

    4.线程的五种状态:

     

    5.常用函数说明:

    5.1:join线程(控制线程):
                    Thread提供了让一个线程等待另一个线程完成的方法--join方法,当在某个程序执行流中调用其他线程的join方法,调用线程将被阻塞,直到被join方法加入的join线程执行完毕为止。

    列子:

     1 /**
     2  * Created by 123 on 2017/07/02.
     3  */
     4 public class TestJoin {
     5     public static void main(String[] args) throws InterruptedException {
     6         new JoinThread("新线程").start();
     7         for (int i = 0; i < 10; i++) {
     8                if (i==5){
     9                    JoinThread j1=new JoinThread("被join的线程");
    10                    j1.start();
    11                    j1.join();
    12                }
    13             System.out.println(Thread.currentThread().getName()+" "+i);
    14         }
    15     }
    16 }
    join方法使用(测试类)
     1 /**
     2  * Created by 123 on 2017/07/02.
     3  */
     4 public class JoinThread extends Thread {
     5     public JoinThread(String name) {
     6         super(name);
     7     }
     8 
     9     public void run(){
    10         for (int i=1;i<=10;i++){
    11             System.out.println(Thread.currentThread().getName()+"  "+i);
    12         }
    13     }
    14 }
    线程执行体

    5.2:yield线程(线程让步):线程的优先级

                    Thread.yield()方法作用是:暂停当前正在执行的线程对象,并执行其他线程。
                    yield()应该做的是让当前运行线程回到可运行状态,以允许具有相同优先级的其他线程获得运行机会。因此,使用yield()的目的是让相同优先级的线程之间能适当的轮转执行。但是,实际中无法保证yield()达到让步目的,因为让步的线程还有可能被线程调度程序再次选中。

     1 import javax.naming.Name;
     2 
     3 /**
     4  * Created by 123 on 2017/07/02.
     5  */
     6 public class ThreadYeild extends Thread {
     7     String name;
     8 
     9     public ThreadYeild(String name) {
    10         super(name);
    11         this.name = name;
    12     }
    13 
    14     @Override
    15     public void run() {
    16         for (int i = 0; i < 50; i++) {
    17             System.out.println(this.getName()+" "+i);
    18             if (i==30){
    19                 Thread.yield();
    20             }
    21         }
    22     }
    23 }
    线程执行体
     1 import javax.naming.Name;
     2 
     3 /**
     4  * Created by 123 on 2017/07/02.
     5  */
     6 public class ThreadYeild extends Thread {
     7     String name;
     8 
     9     public ThreadYeild(String name) {
    10         super(name);
    11         this.name = name;
    12     }
    13 
    14     @Override
    15     public void run() {
    16         for (int i = 0; i < 50; i++) {
    17             System.out.println(this.getName()+" "+i);
    18             if (i==30){
    19                 Thread.yield();
    20             }
    21         }
    22     }
    23 }
    Yeild方法(测试类)

    5.3:sleep()函数和yield函数的区别:

                    sleep()和yield()的区别):
                    1:sleep()使当前线程进入停滞状态,所以执行sleep()的线程在指定的时间内肯定不会被执行;
                    yield()只是使当前线程重新回到可执行状态,所以执行yield()的线程有可能在进入到可执行状态后马上又被执行。
                    2:sleep()函数也可以允许优先级较低的线程运行

    5.4守护线程:

     1 /**
     2  * Created by 123 on 2017/07/02.
     3  */
     4 public class BackGroundThread implements Runnable {
     5     public void run() {
     6          for (int i=1;i<100000000;i++){
     7              System.out.println("后台线程执行第"+i+"次");
     8              try {
     9                  Thread.sleep(7);
    10              } catch (InterruptedException e) {
    11                  e.printStackTrace();
    12              }
    13          }
    14     }
    15 }
    后台线程
     1 /**
     2  * Created by 123 on 2017/07/02.
     3  */
     4 public class MyThreads extends Thread {
     5     @Override
     6     public void run() {
     7         for (int i = 1; i <= 4; i++) {
     8             System.out.println("线程1第" + i + "次执行");
     9             try {
    10                 Thread.sleep(7);
    11             } catch (InterruptedException e) {
    12                 e.printStackTrace();
    13             }
    14         }
    15     }
    16 }
    前台线程
     1 /**
     2  * Created by 123 on 2017/07/02.
     3  * 守护线程
     4  */
     5 public class TestThread {
     6     //如果前台线程执行i次,后台线程执行i+1次,因为还有main线程
     7     public static void main(String[] args) {
     8         Thread t1 = new MyThreads();
     9         Thread t2 = new Thread(new BackGroundThread());
    10         t2.setDaemon(true);    //设置为守护线程
    11         t1.start();
    12         t2.start();
    13     }
    14 }
    测试类

    结论就是:如果前台线程执行i次,那么后台线程就会执行i+1次,因为还有一个main线程。

    5.4:线程的优先级(1~10)
                    setPriority(): 更改线程的优先级。

                MIN_PRIORITY = 1
                     NORM_PRIORITY = 5
                          MAX_PRIORITY = 10

  • 相关阅读:
    (转)PHP 的 __FILE__ 常量
    smarty半小时快速上手教程(转)
    Namespace declaration statement has to be the very first
    ThinkPhp3.2 无法加载模块:Index
    注意mysql中的编码格式和php中的编码格式一致
    MySQL数据库备份与恢复方法(转)
    phpmyadmin设置id自增(AUTO_INCREMENT)(转)
    (转)用eclipse创建一个j2ee的web工程后,左面projects窗口中的项目如何没有显示webRoot文件夹,除了src的文件夹,其他都不显示
    CentOS6.8 安装 Nginx
    Eclipse Java注释模板设置详解
  • 原文地址:https://www.cnblogs.com/quliang/p/7118066.html
Copyright © 2011-2022 走看看