首页 > 系统相关 >线程与进程

线程与进程

时间:2023-06-06 21:55:51浏览次数:31  
标签:Thread 死锁 线程 进程 等待 资源

一、线程与进程的区别

1、进程是程序的一次执行过程,是程序运行的基本单位

2、进程是比线程更小的执行单位,一个进程可以产生多个线程,多个线程共享进程的堆和方法区,每个线程都有自己独立的栈和程序计数器,因此线程之间切换的开销比进程切换小

 

二、并发与并行

并发:同一时间段内,多个线程交替执行

并行:同一时刻多个线程同时执行

三、同步与异步

  • 同步:发出一个调用之后,在没有得到结果之前, 该调用就不可以返回,一直等待。
  • 异步:调用在发出之后,不用等待返回结果,该调用直接返回

四、线程的生命周期和状态(6个)

  • NEW: 初始状态,线程被创建出来但没有被调用 start()
  • RUNNABLE: 运行状态,线程被调用了 start()等待运行的状态。
  • BLOCKED:阻塞状态,需要等待锁释放。
  • WAITING:等待状态,表示该线程需要等待其他线程做出一些特定动作(通知或中断)。
  • TIME_WAITING:超时等待状态,可以在指定的时间后自行返回而不是像 WAITING 那样一直等待。
  • TERMINATED:终止状态,表示该线程已经运行完毕。

sleep与wait对比:

    • sleep() 方法没有释放锁,而 wait() 方法释放了锁
    • wait() 通常被用于线程间交互/通信,sleep()通常被用于暂停执行。
    • wait() 方法被调用后,线程不会自动苏醒,需要别的线程调用同一个对象上的 notify()或者 notifyAll() 方法。sleep()方法执行完成后,线程会自动苏醒,或者也可以使用 wait(long timeout) 超时后线程会自动苏醒。
    • sleep()Thread 类的静态本地方法,wait() 则是 Object 类的本地方法。
     

五、进程的生命周期和状态

  1. 新建状态(New):该状态表示进程已经被创建,但尚未开始执行或分配资源。

  2. 就绪状态(Ready):该状态表示进程已经被分配了所有必要的资源,并已经准备好在处理器上运行,只等待处理器的调度。

  3. 运行状态(Running):该状态表示进程当前正在处理器上执行指令。

  4. 阻塞状态(Blocked):该状态表示进程暂时无法运行,因为它正在等待某些事件的发生,例如 I/O 操作或者信号量等。

  5. 终止状态(Terminated):该状态表示进程已经完成了它的任务,并且被操作系统回收了所有占用的资源。

 

六、线程死锁

多个线程同时被阻塞,它们中的一个或者全部都在等待某个资源被释放。

1、四个必要条件

  • 互斥条件:该资源任意一个时刻只由一个线程占用。
  • 占有并等待条件:一个线程因请求资源而阻塞时,对已获得的资源保持不放。
  • 不可抢占条件:线程已获得的资源在未使用完之前不能被其他线程强行剥夺,只有自己使用完毕后才释放资源。
  • 循环等待条件:若干线程之间形成一种头尾相接的循环等待资源关系

2、如何预防和避免死锁

1、预防死锁

  • 破坏请求与保持条件:一次性申请所有的资源。
  • 破坏不剥夺条件:占用部分资源的线程进一步申请其他资源时,如果申请不到,可以主动释放它占有的资源。
  • 破坏循环等待条件:靠按序申请资源来预防。按某一顺序申请资源,释放资源则反序释放。破坏循环等待条件。
2、避免死锁 分配资源前用银行家算法进行探测,如假设分配资源后系统仍处于安全状态则进行分配 3、检测死锁 使用进程-资源分配图判断是否存在死锁 4、解除死锁     写一个死锁,代码如下:
public class DeadLockDemo {
    private static Object resource1 = new Object();//资源 1
    private static Object resource2 = new Object();//资源 2

    public static void main(String[] args) {
        new Thread(() -> {
            synchronized (resource1) {
                System.out.println(Thread.currentThread() + "get resource1");
                try {
                    Thread.sleep(1000);
                } catch (InterruptedException e) {
                    e.printStackTrace();
                }
                System.out.println(Thread.currentThread() + "waiting get resource2");
                synchronized (resource2) {
                    System.out.println(Thread.currentThread() + "get resource2");
                }
            }
        }, "线程 1").start();

        new Thread(() -> {
            synchronized (resource2) {
                System.out.println(Thread.currentThread() + "get resource2");
                try {
                    Thread.sleep(1000);
                } catch (InterruptedException e) {
                    e.printStackTrace();
                }
                System.out.println(Thread.currentThread() + "waiting get resource1");
                synchronized (resource1) {
                    System.out.println(Thread.currentThread() + "get resource1");
                }
            }
        }, "线程 2").start();
    }
}

  

 

标签:Thread,死锁,线程,进程,等待,资源
From: https://www.cnblogs.com/coooookie/p/17461837.html

相关文章

  • Linux系统下如何保持进程在SSH客户端断开后仍继续运行?
    使用场景在Linux系统中,在执行一些运行时间比较长的任务时,必须等待执行完毕才能断开SSH连接或关闭客户端软件,否则可能会导致执行中断。本文介绍两种保障程序在您退出登录后持续运行的方法。方法1:使用nohup命令1.命令格式nohup,可以使运行的命令忽略SIGHUP信号。因此,即使退出登录......
  • 常见的进程信号
    进程的管理主要是指进程的关闭和重启。我们一般关闭或重启软件,都是关闭或者重启它的程序,而不是直接操作进程的。比如,要重启apache服务,一般使用命令servicehttpdrestart重启apache的程序。那么,可以直接通过管理进程来关闭或重启apache吗?答案是肯定的,这时候就要依赖进程的信号S......
  • 01_多线程
    多线程一、进程与线程1.1、进程:进程:是正在运行的程序是系统进行资源分配和调用的独立单位每个进程都有它自己的内存空间和系统资源 1.2、线程:在一个进程内部,可以执行一个任务,也可以执行多个任务线程:是进程中的单个执行顺序控制流,是一条执行路径单线程:一个进程......
  • Python 多进程之间共享变量
    原文地址:https://blog.51cto.com/alwaysbeta/5162851Python多线程之间共享变量很简单,直接定义全局global变量即可。而多进程之间是相互独立的执行单元,这种方法就不可行了。不过Python标准库已经给我们提供了这样的能力,使用起来也很简单。但要分两种情况来看,一种是Process......
  • C# 线程池ThreadPool的用法简析
    什么是线程池?为什么要用线程池?怎么用线程池?1.什么是线程池?.NETFramework的ThreadPool类提供一个线程池,该线程池可用于执行任务、发送工作项、处理异步I/O、代表其他线程等待以及处理计时器。那么什么是线程池?线程池其实就是一个存放线程对象的“池子(pool)”,他提供了一些基本方......
  • 41.QT-多线程与界面之间交互总结
    1.线程与界面组件需要注意的地方在QThread线程中不能直接创建QWidget之类的界面组件.因为在QT中,所有界面组件相关的操作都必须在主线程中(也就是GUIthread)所以,QThread线程不能直接操作界面组件.2.QThread线程如何操作界面组件-方法1将多线程类对象封装为GUI界面类的类成员然......
  • Java中为什么禁止把SimpleDateFormat定位为static变量以及如果非要使用static定位Simp
    场景Java中ExecutorService线程池的使用(Runnable和Callable多线程实现):https://blog.csdn.net/BADAO_LIUMANG_QIZHI/article/details/126242904Java中创建线程的方式以及线程池创建的方式、推荐使用ThreadPoolExecutor以及示例:https://blog.csdn.net/BADAO_LIUMANG_QIZHI/art......
  • 多线程同步AutoResetEvent 和ManualResetEvent
         ......
  • 如何获取 C#程序 内核态线程栈
    一:背景1.讲故事在这么多的案例分析中,往往会发现一些案例是卡死在线程的内核态栈上,但拿过来的dump都是用户态模式下,所以无法看到内核态栈,这就比较麻烦,需要让朋友通过其他方式生成一个蓝屏的dump,这里我们简单汇总下。二:如何生成内核态dump1.案例代码为了方便演示,来一段简单的......
  • java的线程状态
     New新创建创建一个Thread对象,但还未调用start()启动线程时,线程处于初始态。Runnable可运行在Java中,可运行态包括:Ready和RunningReady就绪态该状态下的线程已经获得执行所需的所有资源,CPU只要分配执行权就能运行。所有就绪态的线程存放在就绪队列中。Running运行中已获得CP......