wait和sleep的区别

本文详细解释了进程与线程的概念及区别,包括它们在操作系统中的角色,并探讨了并发与并行的不同,以及线程状态的变化。通过具体示例说明了sleep与wait方法的工作原理及其在多线程编程中的应用。

进程和线程

进程:进程是一个具有一定独立功能的程序关于某个数据集合的一次运行活动。它是操作系统动态执行的基本单元,在传统的操作系统中,进程既是基本的分配单元,也是基本的执行单元。

线程:通常在一个进程中可以包含若干个线程,当然一个进程中至少有一个线程,不然没有存在的意义,线程可以利用进程所有拥有的资源。在引入线程的操作系统中,通常都是把进程作为分配资源的基本单位,而把线程作为独立运行和独立调度的基本单位,由于线程比进程小,基本上不拥有系统资源,故对它的调度所付出的开销就会小得多,能更高效的提高系统多个程序间并发执行的程度。
 

通常的说进程就是操作系统中运行的一个程序,例如qq.exe等

线程:每个进程中都存在一个或者多个线程,比如用word写文章的时候,就有一个线程在后台帮你保存

并发和并行

并行:多个处理器同时处理多个任务

并发:一个处理器同时处理多个任务

线程的状态:新建、就绪、运行、阻塞、死亡

sleep和wait的区别

1.来自不同的类

sleep来自于Thread类(sleep是thread类的一个静态方法),wait来自object类

2.sleep不会释放锁,wait会释放锁

sleep

package com.qjx;

public class TestSynchorized {
    public static void main(String[] args) throws InterruptedException {
        TestSyn syn1 = new TestSyn();
        Object o = new Object();
        new Thread(() -> {
            syn1.test();
        }, "A").start();

        new Thread(() -> {
            syn1.test();
        }, "B").start();

        new Thread(() -> {
            syn1.test();
        }, "C").start();
    }
}

class TestSyn {
    private int num = 10;

    public synchronized void test() {
        try {
            System.out.println(Thread.currentThread().getName() + "开始了");
            Thread.sleep(3 * 1000);
            System.out.println(Thread.currentThread().getName() + "结束了");
        } catch (InterruptedException e) {
            e.printStackTrace();
        }
    }
}

这里运行的结果是A开始了,然后A结束了,C开始了,C结束了,B开始了,B结束了,所以sleep睡眠的时候会占用着cpu,不给其他线程使用,这里要注意的一个点就是必须是同一把锁

package com.qjx;

public class TestSynchorized {
    public static void main(String[] args) throws InterruptedException {
        TestSyn syn1 = new TestSyn();
        TestSyn syn2 = new TestSyn();
        TestSyn syn3 = new TestSyn();
        Object o = new Object();
        new Thread(() -> {
            syn1.test();
        }, "A").start();

        new Thread(() -> {
            syn2.test();
        }, "B").start();

        new Thread(() -> {
            syn3.test();
        }, "C").start();
    }
}

class TestSyn {
    private int num = 10;

    public synchronized void test() {
        try {
            System.out.println(Thread.currentThread().getName() + "开始了");
            Thread.sleep(3 * 1000);
            System.out.println(Thread.currentThread().getName() + "结束了");
        } catch (InterruptedException e) {
            e.printStackTrace();
        }
    }
}

这里的锁就是当前的对象,因为上面new出来的是三个对象,所以是三个不同的锁那么这里的执行顺序就是

A B C开始了,A B C结束了

wait(这里要注意wait只能用在同步代码块或者同步方法上面)

package com.qjx;

public class WaitTest {
    public static void main(String[] args) {
        WaitT waitT = new WaitT();
        new Thread(()->{
            for (int i = 0; i <10 ; i++) {
                try {
                    waitT.increment();
                } catch (InterruptedException e) {
                    e.printStackTrace();
                }
            }
        },"A").start();

        new Thread(()->{
            for (int i = 0; i <10 ; i++) {
                try {
                    waitT.decrement();
                } catch (InterruptedException e) {
                    e.printStackTrace();
                }
            }
        },"B").start();

    }
}
class WaitT{
    private int num = 0;

    public synchronized void increment() throws InterruptedException {
        //如果num的值不为0,那么就等待,如果num的值是为0,那么就++
        while(num!=0){
            this.wait();
        }
        num++;
        System.out.println(Thread.currentThread().getName()+"的num的值为"+num);
        this.notifyAll();
    }

    public synchronized void decrement() throws InterruptedException {
        while(num==0){
            this.wait();
        }
        num--;
        System.out.println(Thread.currentThread().getName()+"的num的值为"+num);
        this.notifyAll();
    }
}

这里我们看出来,第一次进入的increment方法的时候num++,num的值为1,如果下一次依旧是进入increment方法的话,就会被阻塞,但是这里的阻塞会释放锁,所以当被阻塞的时候,我们是可以进入decreament的方法,然后num--,num=0,并且唤醒线程

3.sleep到时间会自动恢复。wait必须使用notify或者是notifyall进行唤醒

评论 2
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值