首页 > 试题广场 >

请你说说线程和协程的区别

[问答题]
表面上看协程和线程似乎是同一个东西,能达到的效果也相同,但是在底层的实现上却有着非常大的区别,在服务器端的绝大部分应用中,协程要比线程节省资源的多。 通俗易懂的讲,线程是操作系统的资源,当java程序创建一个线程,虚拟机会向操作系统请求创建一个线程,虚拟机本身没有能力创建线程。而线程又是昂贵的系统资源,创建、切换、停止等线程属性都是重量级的系统操作,非常消耗资源,所以在java程序中每创建一个线程都需要经过深思熟虑的思考,否则很容易把系统资源消耗殆尽。 而协程,看起来和线程差不多,但创建一个协程却不用调用操作系统的功能,编程语言自身就能完成这项操作,所以协程也被称作用户态线程。我们知道无论是java还是go程序,都拥有一个主线程,这个线程不用显示编码创建,程序启动时默认就会创建。协程是可以跑在这种线程上的,你可以创建多个协程,这些协程跑在主线程上,它们和线程的关系是一对多。如果你要创建一个线程,那么你必须进行操作系统调用,创建的线程和主线程是同一种东西。显然,协程比线程要轻量的多。 既然协程这么优秀,为什么不彻底替代线程呢?事实上协程和线程完全不是两个相同层面的东西,完全谈不上替代一说,协程可以说是一个独立于线程的功能,它是在线程的基础上,针对某些应用场景进一步发展出来的功能。我们知道,线程在多核的环境下是能做到真正意义上的并行执行的,注意,是并行,不是并发,而协程是为并发而生的。 打个简单的比方吧,射雕英雄传看过吧,周伯通教郭靖一手画圆,一手画方,两只手同时操作,左右互搏,这个就是并行。普通人肯定做不到,不信你试试。你不能并行,却可以并发,你先左手画一笔,然后右手画一笔,同一时候只有一只手在操作,来回交替,直到完成两个图案是,这就是并发,协程主要的功能。 想象一下业务场景,你需要执行两个互不依赖的sql查询,为了减少等待时间,常规的操作肯定主线程执行sqlB的同时另起一个线程执行sqlA,使两个sql并行执行。然而你会发现,执行两个sql的线程大多数时间只是在等待数据库服务器的响应,线程只是处于阻塞等待状态,而不是疯狂运转,而线程的创建、切换又很消耗系统资源,显然这很浪费。这个时候就该协程大展身手了,你可以在主线程中创建一个协程用于执行sqlB,然后再在主线程中执行sqlA,协程和线程一样,不会阻塞主线程,所以sqlB得到结果后,你可以通过语言的api去看看在协程中的sql执行完毕了没有,如果没有则等待,如果执行完毕了就拿结果,和线程操作几乎一摸一样。至于sqlA和sqlB是否真正在并行执行根本无所谓。为什么呢? 我们假设执行一个sql需要三步,提交sql、等待、获得结果 ,其中第一步和第三步极省时,只要1毫秒一步,而第二步却要1000毫秒,那么使用并行的多线程执行两个sql,你只要花掉1002毫秒,而使用并发的协程你要花掉1004毫秒,但是线程比协程多消耗一个线程的资源,请问你会为了这2毫秒而选择多线程吗,显然不可能,创建线程的开销都要大于节省下来的时间,这就是协程存在的理由。 而服务器端开发中,大多数时候都是要花大量等待时间的场景,也就是所谓的IO密集,协程极为适合这种场景,而go又主打协程,直接从语法层面支持,切中了以往开发高性能程序太过于复杂的痛点,因此广受程序员们的欢迎。java其实也可以模拟出协程的效果,比如用nio和多线程,也能假装goroutines的效果,但实际操作起来太过于麻烦,还要掌握一大堆枯涩的概念,完全没有goroutines的优雅。所以在并发性能上,go完胜java。换言之,go比java更适应高并发场景,能更优雅方便的写出高并发程序。
发表于 2022-08-18 15:34:39 回复(2)
1、一个线程可以有多个协程,一个进程也可以单独有多个协程。 2、线程是同步的,协程是异步的。 3、线程是抢占式的,协程是非抢占式的,所以需要用户释放使用权来切换给其他协程,因此同一时间只有一个协程拥有执行权。 4、线程是协程的资源,协程通过intercepor间接使用线程这个资源。
发表于 2022-07-16 11:40:02 回复(0)
1、线程是操作系统的资源,线程的创建、切换、停止等操作都非常的消耗资源,而协程的创建不需要调用系统的功能,编程语言自身就能完成 2、线程在多核环境下能够做到真正意义上的并行,而协程是为并发产生的 3、一个具有多个线程的程序可以同时运行多个线程,而协同程序需要彼此协作的运行 4、线程属于同步机制,而协同是异步 5、线程是抢占式,而协程是非抢占式,所以需要用户自己释放使用权来切换到其它协程,因此同一时间只有一个协程具有运行权 6、操作系统能够创建数量为千的线程,但是能够创建上万的协程
发表于 2022-07-03 11:00:53 回复(0)
1.线程是进程的子集,一个进程可以包含多个线程,每个线程执行不同的任务 2.每个进程使用不同的内存空间,所有的线程共享一个相同的内存空间 3.每个线程用单独的栈内存来存储本地数据
发表于 2022-04-24 11:17:08 回复(2)
协程是线程的抽象单位,减少了线程切换过程中的资源代价
发表于 2022-07-13 21:00:08 回复(0)
线程和协程都是实现并发处理的方式,但是它们之间有以下几个区别: 调度方式:线程的调度是由操作系统负责的,而协程的调度是由应用程序自己控制的。线程的切换需要进行上下文切换,开销较大,而协程的切换成本较低,可以更高效地利用CPU资源。 资源占用:每个线程都有自己独立的堆栈空间,占用内存较大,而协程通常共享同一个堆栈空间,占用内存较小。 线程安全:由于多个线程共享进程的资源,因此线程之间的共享数据需要进行同步控制,避免出现数据竞争等问题。而协程通常不需要进行同步控制,因为协程之间的数据共享通常是通过消息传递实现的。 编程模型:线程通常采用共享内存模型,需要进行同步控制,而协程通常采用消息传递模型,不需要进行同步控制。 创建销毁:线程的创建和销毁比协程开销更大,因为线程需要分配新的栈空间,而协程通常共享同一个堆栈空间。 需要注意的是,线程和协程都是实现并发处理的方式,应该根据实际需求选择合适的并发处理方式。在实际应用中,通常采用多线程和协程相结合的方式来实现高效的并发处理。
发表于 2023-04-18 11:38:14 回复(0)
1、协程就是可以暂停执行的函数;2、一个进程中可以有多个线程,一个线程中可以有多个协程;3、协程是由程序控制的,在用户态。4、线程和进程是同步机制,协程是异步的;5、线程是抢占式的,协程是非抢占式。
发表于 2023-03-25 11:13:56 回复(0)
1.线程是操作系统的资源,线程的创建、切换、停止等都非常消耗资源,
2.协程不需要调用操作系统的功能,编程语言自身就能完成,所以协程也被称为用户态线程,协程比线程轻量很多;
3.线程在多核环境下是能做到真正意义上的并行,而协程是为并发而产生的;
4.线程进程都是同步机制,而协程则是异步;
5.线程是抢占式,而协程是非抢占式的,所以需要用户自己释放使用权来切换到其他协程,因此同一时间其实只有一个协程拥有运行权,相当于单线程的能力;
发表于 2023-01-17 01:36:36 回复(0)
1.线程是创建、切换、停止都是要调用操作系统来实现的,协程则可以通过编程语言实现 2.进程、线程是同步的,协程是异步的 3.线程是抢占式,协程是非抢占式,需要用户主动释放cpu 4.线程在多核状态能实现并行,而协程是为了用来支持并发的
发表于 2022-07-26 15:03:47 回复(0)
线程是操作系统自身的资源,线程的创建,切换,停止都十分消耗资源,而创建协程不需要调用操作系统的功能,编程语言自身就可以完成,所以协程也被称为用户态线程,协程比线程轻量很多。 线程只有在多核环境下才可以真正意义上的并行,而协程就是为并发而产生的。 一个具有多线程的程序可以同时运行几个线程,而协程需要彼此之间的协作,线程和进程都是同步机制,而协程是异步机制,一个线程可以拥有多个协程,一个进程也可以拥有多个协程。 线程是抢占式,而协程是非抢占式,需要用户释放使用权切换到其他协程,因此同一时间其实只能有一个协程拥有运行权,相当于单线程的能力。 协程不被操作系统内核管理,而完全由程序控制,线程是被分割的CPU资源,协程是组织好的代码流程,线程是协程的资源。但协程不会直接使用线程,协程直接利用的是执行器关联任意线程或线程池。 协程能保留上一次调用时的状态。
发表于 2022-07-20 20:17:57 回复(0)
1.线程是操作系统的资源,线程的创建、切换、停止等都非常消耗资源, 2.协程不需要调用操作系统的功能,编程语言自身就能完成,所以协程也被称为用户态线程,协程比线程轻量很多; 3.线程在多核环境下是能做到真正意义上的并行,而协程是为并发而产生的; 4.线程进程都是同步机制,而协程则是异步; 5.线程是抢占式,而协程是非抢占式的,所以需要用户自己释放使用权来切换到其他协程,因此同一时间其实只有一个协程拥有运行权,相当于单线程的能力
编辑于 2024-04-02 19:57:17 回复(0)
1、线程是操作系统的资源,线程的创建、切换、停止非常消耗资源 2、协程不需要操作系统的功能,编程语言自带的,称为用户态线程,轻量 3、在多核下,线程可以实现并行,协程不能 4、线程抢占式、协程协作式,共享线程的栈和堆
编辑于 2024-03-16 16:55:54 回复(0)
编辑于 2024-03-08 15:23:24 回复(0)
线程(Thread)和协程(Coroutine)是两种并发编程的方式,它们在实现并发和并行任务时有一些重要的区别。 1、执行单位: 线程是由操作系统内核进行管理和调度的最小执行单位。每个线程都有自己的堆栈和程序计数器,以及共享的进程资源,如堆内存、全局变量等。 协程则是由程序控制器,即编程语言运行环境进行调度的执行单位。可以在需要时暂停和恢复执行,而不会切换线程。 2、调度方式: 线程使用抢占式调度算法 协程通常使用协作式调度算法。 3、切换开销: 线程的切换涉及到内核态和用户态的切换,因此开销比较大。 协程切换过程中只涉及用户态的操作,因此切换开销比线程小很多。 4、并发性和并行性: 一个进程可以包含多个线程,这些线程可以并行执行,利用多核处理器的性能。 协程通常在单线程内执行,但可以通过多个协程实现并发任务。 5、共享资源: 线程之间共享进程的资源,因此需要通过锁、信号量等机制来保护共享资源的访问,避免竞态条件和数据不一致问题。 协程通常在同一个线程内执行,它们可以共享线程的栈和堆内存,因此不存在线程之间的资源竞争问题。
发表于 2024-02-26 14:11:31 回复(0)
一个线程可以有多个协程,一个进程也可以单独拥有多个协程。线程是同步的,协程是异步的。线程是抢占式的,协程是非抢占性的,线程是协程的资源,协程通过intercepor间接使用线程这个资源
发表于 2023-08-14 10:17:09 回复(0)
1、一个线程可以有多少协程,一个进程也可以单独有多个协程。2、线程是同步的,协程是异步的。3、线程是抢占式的,协程是非抢占式的,所以需要用户释放使用权来切换给其他协程,因此同一时间只有一个协程拥有执行权。4、线程是协程的资源,协程通过intercepor间接使用线程这个资源。
发表于 2023-04-10 12:25:28 回复(0)
协程是一种用户态的轻量级线程,协程的调度完全由用户态决定。 协程最大的优势是协程极高的执行效率。因为它不是线程切换,而是由程序自身控制。 1. 一个线程可以有多个协程。 2. 线程是抢占式的, 协程是非抢占式的。需要用户释放使用权来切换协程,因此同一时间是只有一个协程拥有运行权。 3. 线程是被分割CPU的资源,协程是组织好的代码流程。
发表于 2023-04-02 19:45:01 回复(0)
1、一个线程可以有多个协程,一个进程也可以单独有多个协程。 2、线程是同步的,协程是异步的。 3、线程是抢占式的,协程是非抢占式的,所以需要用户释放使用权来切换给其他协程,因此同一时间只有一个协程拥有执行权。 4、线程是协程的资源,协程通过intercepor间接使用线程这个资源。
发表于 2023-03-08 15:05:59 回复(0)
线程是操作系统的资源,线程的创建,切换,停止,都需要消耗系统资源,协程的创建不需要可以由编程语言实现。一个操作系统可以开辟千个线程,协程则可以开辟上万个。协程是一个轻量级线程。在操作系统内核条件允许的情况下,线程可以做到并行执行,而协程只能并发。线程是抢占式协程是非抢占式。线程比协程更好控制。线程对共享资源的使用需要加锁,协程不需要,只需要判断状态就行了。
发表于 2023-03-02 13:58:05 回复(0)
线程和协程:1.线程切换创建等需要消耗资源,但是协程是编程语言自己完成,不用调用系统功能,不hao资源。 2. 一个多线程程序可以同时运行多个线程,但是一个协程程序需要多个协程合作完成 3.线程是同步的,协程是异步的;线程是抢占式的,协程是非抢占性
编辑于 2023-02-22 09:48:53 回复(0)