zoukankan      html  css  js  c++  java
  • Java多线程基础(一)

    1.什么是进程、线程

      进程可以简单的理解为应用程序。多线程,相当于多个人共同完成一件事情,每个线程,独立完成一件任务。因此,一个进程至少有一个线程,一个线程不能独立存在,它必须是进程的一部分。

      进程:每个独立运行着的程序。具有独立的内存空间和系统资源。(建大厦)

      线程:是一个进程内部的一条执行路径。是系统独立调度和分配CPU的最小单位。(搬砖头)

    2.创建线程的方式(三种)

    • 1.通过实现 Runnable 接口;(存在共享资源时使用——是否是相同操作)
    • 2.通过继承 Thread 类本身;(没有共享资源时可用)
    • 3.通过 Callable 和 Future 创建线程。(JDK1.5开始引入)

        对比:

    • 1. 采用实现 Runnable、Callable 接口的方式创建多线程时,线程类只是实现了 Runnable 接口或 Callable 接口,还可以继承其他类。

    • 2. 使用继承 Thread 类的方式创建多线程时,编写简单,如果需要访问当前线程,则无需使用 Thread.currentThread() 方法,直接使用 this 即可获得当前线程。

    3.线程的状态及特性

    线程具有随机性:谁能抢到CPU,谁执行。 

    package com.test;
    public class ThreadDemo1 { public static void main(String[] args) { // TODO Auto-generated method stub MyThread myThread=new MyThread("name"); //myThread.run();//主线程 myThread.start();//多线程 } } class MyThread extends Thread{ public MyThread() { super(); // TODO Auto-generated constructor stub } public MyThread(String name) { super(name); } public void run() { for(int i=0;i<20;i++) { System.out.println(Thread.currentThread().getName()+"→"+i); } } }

    创建线程,输出1~100之间的偶数。要求使用线程实现,继承Thread类

    package com.test;
    
    public class ThreadDemo2 {
    
        public static void main(String[] args) {
            // TODO Auto-generated method stub
            OutputEven outputEven=new OutputEven();
            outputEven.start();
        }
    
    }
    class OutputEven extends Thread{
    
        @Override
        public void run() {
            // TODO Auto-generated method stub
            for(int i=1;i<=100;i++) {
                if(i%2==0) {
                    System.out.println(Thread.currentThread().getName()+"→"+i);
                }
            }
        }
        
    }

     使用线程模拟四个工人搬砖场景,谁抢到托运机谁去搬砖

    package com.test;
    
    public class ThreadDemo3 {
    
        public static void main(String[] args) {
            // TODO Auto-generated method stub
            Worker worker1=new Worker("张三1","搬砖");
            Worker worker2=new Worker("张三2","搬砖");
            Worker worker3=new Worker("张三3","搬砖");
            Worker worker4=new Worker("张三4","搬砖");
            worker1.start();
            worker2.start();
            worker3.start();
            worker4.start();
            
        }
    
    }
    class Worker extends Thread{
        String name;
        String task;
        
        public Worker() {
            // TODO Auto-generated constructor stub
            super();
        }
        
        public Worker(String name, String task) {
            super();
            this.name = name;
            this.task = task;
        }
    
        @Override
        public void run() {
            // TODO Auto-generated method stub
            work();
        }
        public void work() {
            System.out.println(name+"正在"+task);
        }
    }

    三个窗口都可以卖100张票。

    package com.test;
    
    public class ThreadDemo4 {
    
        public static void main(String[] args) {
            // TODO Auto-generated method stub
            WinTicket winTicket1=new WinTicket("窗口1");
            WinTicket winTicket2=new WinTicket("窗口2");
            WinTicket winTicket3=new WinTicket("窗口3");
            winTicket1.start();
            winTicket2.start();
            winTicket3.start();
            
        }
    
    }
    class WinTicket extends Thread{
        private int ticket=100;
    
        public WinTicket() {
            super();
            // TODO Auto-generated constructor stub
        }
        public WinTicket(String name) {
            super(name);
        }
        @Override
        public void run() {
            // TODO Auto-generated method stub
            while(true) {
                if(ticket>0) {
                    String name=Thread.currentThread().getName();
                    System.out.println(name+"卖出"+ticket--);
                }else {
                    break;
                }
            }
        }
        
    } 

     4.多个线程共享资源

      三个窗口共同卖100张票。

    package com.test;
    
    public class ThreadDemo5 {
    
        public static void main(String[] args) {
            // TODO Auto-generated method stub
            //创建共享资源对象
            TicketRes ticketRes=new TicketRes();
            //创建线程对象
            Thread w1=new Thread(ticketRes,"窗口1");
            Thread w2=new Thread(ticketRes,"窗口2");
            Thread w3=new Thread(ticketRes,"窗口3");
            w1.start();
            w2.start();
            w3.start();
        }
    }
    //共享资源类
    class TicketRes implements Runnable{
        private int ticket=100;
        
        @Override
        public void run() {
            // TODO Auto-generated method stub
            while(true) {
                if(ticket>=1) {
                    System.out.println(Thread.currentThread().getName()+"卖第"+ticket+"张票");
                    ticket--;
                }else {
                    break;
                }
            }
        }
    }
    //出现一个问题:第一百张票会同时在三个窗口卖出。这个涉及到同步和异步的问题?该怎么解决呢?Java多线程基础(二)揭晓答案

    5.线程调度

    优先级 

      优先级用1-10表示,1的优先级最低,10的优先级最高,默认情况为5

      setPriority(int grade);

    调度方法

      join():阻塞指定的线程等到另一个线程完成以后再执行 

    package com.test;
    
    public class JoinDemo {
    
        public static void main(String[] args) throws InterruptedException {
            // TODO Auto-generated method stub
            System.out.println("主线程在执行...");
            JoinThread joinThread1=new JoinThread("线程1");
            JoinThread joinThread2=new JoinThread("线程2");
            JoinThread joinThread3=new JoinThread("线程3");
            System.out.println("启动子线程...");
            joinThread1.start();
            joinThread2.start();
            joinThread3.start();
            joinThread1.join();
            joinThread2.join();
            joinThread3.join();
            for(int i=0;i<10;i++) {
                System.out.println("主线程正在执行...");
            }
            System.out.println("结束");
        }
        
    
    }
    class JoinThread extends Thread{
        
        public JoinThread() {
            super();
            // TODO Auto-generated constructor stub
        }
        
        public JoinThread(String name) {
            super(name);
            // TODO Auto-generated constructor stub
        }
    
        @Override
        public void run() {
            // TODO Auto-generated method stub
            for(int i=0;i<10;i++) {
                System.out.println(Thread.currentThread().getName()+"→"+i);
            }
        }
        
    }
    View Code

      sleep():会暂时释放CPU, 让给其他线程执行, 即使没有其他线程抢占CPU,也需要等待睡眠时间到了以后才能真正的指定

    package com.test;
    
    public class SleepDemo {
    
        public static void main(String[] args){
            // TODO Auto-generated method stub
            SleepThread sleepThread=new SleepThread();
            sleepThread.start();
        }
    
    }
    class SleepThread extends Thread{
        
        public SleepThread() {
            super();
            // TODO Auto-generated constructor stub
        }
        
        public SleepThread(String name) {
            super(name);
            // TODO Auto-generated constructor stub
        }
    
        @Override
        public void run() {
            // TODO Auto-generated method stub
            for(int i=10;i>=0;i--) {
                try {
                    Thread.sleep(1000);
                    System.out.println(i);
                } catch (InterruptedException e) {
                    // TODO Auto-generated catch block
                    e.printStackTrace();
                }
            }
        }
        
    }
    View Code

      yield():执行的时候会让出CPU , 但是会立马同其他的线程抢占CPU

    package com.test;
    
    public class YieldDemo {
    
        public static void main(String[] args) {
            // TODO Auto-generated method stub
            YieldThread yieldThread1=new YieldThread("线程1");
            YieldThread yieldThread2=new YieldThread("线程2");
            yieldThread1.start();
            yieldThread2.start();
        }
    
    }
    class YieldThread extends Thread{
        
        public YieldThread() {
            super();
            // TODO Auto-generated constructor stub
        }
        
        public YieldThread(String name) {
            super(name);
            // TODO Auto-generated constructor stub
        }
    
        @Override
        public void run() {
            // TODO Auto-generated method stub
            for(int i=0;i<20;i++) {
                System.out.println(Thread.currentThread().getName()+"→"+i);
                Thread.yield();//避让,谦让,让出CPU,还有再去抢的资格
            }
        }
        
    }
    View Code
  • 相关阅读:
    数据库表结构变动发邮件脚本
    .net程序打包部署
    无法登陆GitHub解决方法
    netbeans 打包生成 jar
    第一次值班
    RHEL6 纯命令行文本界面下安装桌面
    C语言中格式化输出,四舍五入类型问题
    I'm up to my ears
    How to boot ubuntu in text mode instead of graphical(X) mode
    the IP routing table under linux@school
  • 原文地址:https://www.cnblogs.com/loober/p/10193332.html
Copyright © 2011-2022 走看看