Java多线程

程序、进程、线程

程序

程序是指令和数据的有序集合,是一个静态的概念

进程(process)

进程是程序的一次执行过程,是动态的概念,是系统资源分配的单位

线程(Thread)

通常在一个进程中可以包含若干个线程,当然一个进程中至少有一个线程,线程是CPU调度和执行的单位

 

线程三种创建方式

继承Thread类

package com.henry.thread;
//继承Thread类,重写run方法,调用start开启线程
public class TestThread extends Thread{
    @Override
    public void run() {
        for (int i = 0; i < 10; i++) {
            System.out.println("x+"+i);
        }
    }
​
    public static void main(String[] args) {
        //创建一个线程对象
        TestThread testThread = new TestThread();
        //调用start方法开启线程
        testThread.start();
        //main线程,主线程
        for (int i = 0; i < 1000 ; i++) {
            System.out.println("y+"+i);
        }
    }
}

 

多线程下载图片

package com.henry.thread;
​
import org.apache.commons.io.FileUtils;
​
import java.io.File;
import java.io.IOException;
import java.net.URL;
​
public class TestThread2 extends Thread{
    private String url;
    private String filename;
​
    public TestThread2(String url, String filename) {
        this.url = url;
        this.filename = filename;
    }
​
    @Override
    public void run() {
        WebDownloader webDownloader = new WebDownloader();
        webDownloader.downloader(url,filename);
        System.out.println("下载了文件名为:"+filename);
    }
​
    public static void main(String[] args) {
        TestThread2 t1 = new TestThread2("https://img2020.cnblogs.com/blog/2035046/202008/2035046-20200829165338623-1016877944.png","1.png");
        TestThread2 t2 = new TestThread2("https://img2020.cnblogs.com/blog/2035046/202008/2035046-20200829170405010-1982825617.png","2.png");
        TestThread2 t3 = new TestThread2("https://pic.cnblogs.com/avatar/2035046/20200511235307.png","3.png");
        t1.start();
        t2.start();
        t3.start();
        //下载了文件名为:2.png
        //下载了文件名为:1.png
        //下载了文件名为:3.png
    }
}
​
​
class WebDownloader{
    public void downloader(String url,String name){
        try {
            FileUtils.copyURLToFile(new URL(url),new File(name));
        } catch (IOException e) {
            e.printStackTrace();
        }
    }
}

 

 

实现Runnable接口

package com.henry.thread;
​
//创建线程方式2:实现runnable接口,重写run方法,执行线程需要runnable接口实现类
public class TestThread3 implements Runnable{
    public void run() {
        for (int i = 0; i < 10; i++) {
            System.out.println("x+"+i);
        }
    }
​
    public static void main(String[] args) {
        //创建runnable接口的实现类对象
        TestThread3 testThread3 = new TestThread3();
        //创建线程对象,通过线程对象开启我们的线程
        
        new Thread(testThread3).start();
        for (int i = 0; i < 1000 ; i++) {
            System.out.println("y+"+i);
        }
    }
}

 

多线程下载图片

package com.henry.thread;
​
import org.apache.commons.io.FileUtils;
​
import java.io.File;
import java.io.IOException;
import java.net.URL;
​
public class TestThread2 implements Runnable{
    private String url;
    private String filename;
​
    public TestThread2(String url, String filename) {
        this.url = url;
        this.filename = filename;
    }
​
    public void run() {
        WebDownloader webDownloader = new WebDownloader();
        webDownloader.downloader(url,filename);
        System.out.println("下载了文件名为:"+filename);
    }
​
    public static void main(String[] args) {
        TestThread2 t1 = new TestThread2("https://img2020.cnblogs.com/blog/2035046/202008/2035046-20200829165338623-1016877944.png","1.png");
        TestThread2 t2 = new TestThread2("https://img2020.cnblogs.com/blog/2035046/202008/2035046-20200829170405010-1982825617.png","2.png");
        TestThread2 t3 = new TestThread2("https://pic.cnblogs.com/avatar/2035046/20200511235307.png","3.png");
        new Thread(t1).start();
        new Thread(t2).start();
        new Thread(t3).start();
        //下载了文件名为:2.png
        //下载了文件名为:1.png
        //下载了文件名为:3.png
    }
}
​
​
​
class WebDownloader{
    public void downloader(String url,String name){
        try {
            FileUtils.copyURLToFile(new URL(url),new File(name));
        } catch (IOException e) {
            e.printStackTrace();
        }
    }
}

 

 

实现Callable接口

package com.henry.thread;
​
import org.apache.commons.io.FileUtils;
​
import java.io.File;
import java.io.IOException;
import java.net.URL;
import java.util.concurrent.*;
​
public class TestThread2 implements Callable<Boolean> {
    private String url;
    private String filename;
​
    public TestThread2(String url, String filename) {
        this.url = url;
        this.filename = filename;
    }
​
    public Boolean call() {
        WebDownloader webDownloader = new WebDownloader();
        webDownloader.downloader(url,filename);
        System.out.println("下载了文件名为:"+filename);
        return true;
    }
​
    public static void main(String[] args) throws ExecutionException, InterruptedException {
        TestThread2 t1 = new TestThread2("https://img2020.cnblogs.com/blog/2035046/202008/2035046-20200829165338623-1016877944.png","1.png");
        TestThread2 t2 = new TestThread2("https://img2020.cnblogs.com/blog/2035046/202008/2035046-20200829170405010-1982825617.png","2.png");
        TestThread2 t3 = new TestThread2("https://pic.cnblogs.com/avatar/2035046/20200511235307.png","3.png");
​
        //创建执行服务
        ExecutorService service = Executors.newFixedThreadPool(3);
        //提交执行
        Future<Boolean> r1 = service.submit(t1);
        Future<Boolean> r2 = service.submit(t2);
        Future<Boolean> r3 = service.submit(t3);
        //获取结果
        Boolean rb1 = r1.get();
        Boolean rb2 = r2.get();
        Boolean rb3 = r3.get();
        //关闭服务
        service.shutdownNow();
    }
}
​
​
​
class WebDownloader{
    public void downloader(String url,String name){
        try {
            FileUtils.copyURLToFile(new URL(url),new File(name));
        } catch (IOException e) {
            e.printStackTrace();
        }
    }
}

 

 

 

龟兔赛跑问题

package com.henry.thread;
​
public class Race implements Runnable{
    private String winner;
    public void run() {
        for (int i = 0; i <= 100; i++) {
            if(Thread.currentThread().getName().equals("兔子") && i%10==0){
                try {
                    Thread.sleep(1);
                } catch (InterruptedException e) {
                    e.printStackTrace();
                }
            }
            boolean flag = gameOver(i);
            if(flag){
                break;
            }
            System.out.println(Thread.currentThread().getName()+"跑了"+i+"步");
        }
    }
​
    private boolean gameOver(int steps){
        if(winner != null){
            return true;
        }else {
            if(steps >= 100){
                winner = Thread.currentThread().getName();
                System.out.println("winner is "+winner);
                return true;
            }
        }
        return false;
    }
​
    public static void main(String[] args) {
        Race race = new Race();
        new Thread(race,"兔子").start();
        new Thread(race,"乌龟").start();
    }
}

 

 

并发问题

package com.henry.thread;
​
public class TestThread4 implements Runnable{
    private int ticketNum =10;
​
    public void run() {
        while(true){
            if(ticketNum<=0){
                break;
            }
            try {
                Thread.sleep(10);
            } catch (InterruptedException e) {
                e.printStackTrace();
            }
            System.out.println(Thread.currentThread().getName()+"拿到了第"+ticketNum--+"票");
        }
    }
​
    public static void main(String[] args) {
        TestThread4 testThread4 = new TestThread4();
​
        new Thread(testThread4,"记得").start();
        new Thread(testThread4,"单独").start();
        new Thread(testThread4,"安安").start();
        
        //多个线程操作同一个资源,线程不安全,数据紊乱
    }
}

 

 

posted @ 2020-10-12 17:08  Henry829  阅读(89)  评论(0编辑  收藏  举报