协程

golang goroutine的调度

℡╲_俬逩灬. 提交于 2019-12-18 09:12:22
golang goroutine的调度 1、什么是协程? 协程是一种用户态的轻量级线程。 2、进程、线程、协程的关系和区别: * 进程拥有自己独立的堆和栈,既不共享堆,亦不共享栈,进程由操作系统调度。 * 线程拥有自己独立的栈和共享的堆,共享堆,不共享栈,线程亦由操作系统调度(标准线程是的)。 * 协程和线程一样共享堆,不共享栈,协程由程序员在协程的代码里显示调度。 * 协程和线程的区别是:协程避免了无意义的调度,由此可以提高性能。 * 执行协程只需要极少的栈内存(大概是4~5KB),默认情况下,线程栈的大小为1MB。 goroutine就是一段代码,一个函数入口,以及在堆上为其分配的一个堆栈。所以它非常廉价,我们可以很轻松的创建上万个goroutine,但它们并不是被操作系统所调度执行。 runtime。GOMAXPROCS(runtime。NumCPU()) // go version>=1.5的时候,GOMAXPROCS的默认值就是go程序启动时可见的操作系统认为的CPU个数。 注意:在go程序中使用的操作系统线程数量包括:正服务于cgo calls的线程,阻塞于操作系统calls的线程,所以go程序中使用的操作系统线程数量可能大于GOMAXPROCS的值。 3、调度 要理解协程的实现,首先需要了解go中的三个非常重要的概念,它们分别是G(goroutine)、M

Go语言 进程、线程、轻量级进程、协程和go中的Goroutine 那些事儿

独自空忆成欢 提交于 2019-12-18 03:46:03
原文: http://www.cnblogs.com/shenguanpu/archive/2013/05/05/3060616.html 电话面试被问到go的协程,曾经的军伟也问到过我协程。虽然用python时候在Eurasia和eventlet里了解过协程,但自己对协程的概念也就是轻量级线程,还有一个很通俗的红绿灯说法:线程要守规则,协程看到红灯但是没有车仍可以通行。现在总结各个资料,从个人理解上说明下 进程 线程 轻量级进程 协程 go中的goroutine 那些事儿。 一、进程 操作系统中最核心的概念是进程,分布式系统中最重要的问题是进程间通信。 进程 是“程序执行的一个实例” ,担当分配系统资源的实体。进程创建必须分配一个完整的独立地址空间。 进程切换 只发生在内核态,两步:1 切换页全局目录以安装一个新的地址空间 2 切换内核态堆栈和硬件上下文。 另一种说法类似:1 保存CPU环境(寄存器值、程序计数器、堆栈指针)2修改内存管理单元MMU的寄存器 3 转换后备缓冲器TLB中的地址转换缓存内容标记为无效。 二、线程 书中的定义:线程是进程的一个执行流,独立执行它自己的程序代码。 维基百科: 线程 ( 英语 : thread )是 操作系统 能够进行运算 调度 的最小单位。 线程上下文一般只包含CPU上下文及其他的线程管理信息

【转】libgo

北慕城南 提交于 2019-12-18 02:53:42
原文: https://blog.csdn.net/libaineu2004/article/details/80554870 ---------------------------------------------------------- Kiev框架简介 kiev是魅族科技推送平台目前使用的Linux-C++后台开发框架。从2012年立项起,先后由多位魅族资深架构师、资深C++工程师倾力打造,到本文写就的时间为止,已经在推送平台这个千万用户级的大型分布式系统上经历了近5年的考验。如今Kiev在魅族推送平台中,每天为上百个服务完成数百亿次RPC调用。 kiev作为一套完整的开发框架,是专为大型分布式系统后台打造的C++开发框架,由以下几个组件组成: RPC框架(TCP/UDP) FastCGI框架 redis客户端(基于hiredis封装) mysql客户端(基于mysqlclient封装) mongodb客户端 配置中心客户端(Http协议, 基于curl实现) 基于zookeeper的分布式组件(服务发现、负载均衡) 日志模块 状态监控模块 核心模块是一个开源的`CSP并发模型`协程库(libgo) 并发模型 Kiev采用了很先进的CSP开发模型的一个变种(golang就是这种模型),这一模型是继承自libgo的。

[RUST]async-std协程库

这一生的挚爱 提交于 2019-12-16 10:23:05
Rust版本: stable 1.39 安装crate: [dependencies] async-std = "*" 简单使用(基于manager-workers模型): use async_std::{task, }; type Result<T> = std::result::Result<T, Box<dyn std::error::Error + Send + Sync>>; async fn manager() -> Result<()> { task::spawn(worker()); Ok(()) } async fn worker() -> Result<()> { Ok(()) } fn main() { task::block_on(manager()); } 来源: CSDN 作者: XiaoH0_0 链接: https://blog.csdn.net/XiaoH0_0/article/details/103548549

进程、线程、协程

爱⌒轻易说出口 提交于 2019-12-15 20:20:51
一、进程   --定义:程序运行起来后,代码及程序所需要的资源(包含内存、变量、硬件等)的总和为一个进程。进程是资源分配的单位,可以理解为内存中分配的一块区域。 二、线程   --定义:每个进程中默认会有一个线程,此线程即为主线程,主线程是CPU能够调度的最小单位,真正执行程序时,是线程在动态的执行代码,进程只是一个资源的总和。 三、协程   --定义:协程也是一个线程,是一个在遇到IO阻塞进行任务切换的一个特殊的线程。协程通过gevent方法实现,gevent的底层实现是greenlet,greenlet的底层实现是yield,当程序(生成器)遇到yield时会阻塞,此时会返回到主程序中,主程序再去调度其他的函数。协程一定属于一个线程,因此协程肯定是通过并发实现的多任务。 四、相同点   --三者都是实现多任务的一种方式 五、不同点   --三者内存开销不一样,进程最大、线程次之、协程最小   --进程是资源分配的最小单位,包含代码和资源   --进程更稳定,一个进程的崩溃不会引起其他进程的崩溃   --线程是CPU调度的最小单位,代码的真正执行时通过线程实现的   --主线程的崩溃会引起其他线程的崩溃   --协程也是一个线程,是一个可以任务切换的线程   --协程需要的资源最少,效率最高,线程次之,进程最低   --根据CPU核数不同,多进程、多线程可能是并行的

swoole入门之协程的示例

有些话、适合烂在心里 提交于 2019-12-15 19:31:45
对协程的理解和实现 可以理解成 使用同步的代码 实现 异步的功能 这里 使用redis组件 是说明这句话 在使用组件之前 需要确认环境中的swoole环境 是否开启了 async-redis的这个配置 、 如果没有的话 建议对swoole进行重新编译 可参考这里 https://blog.csdn.net/zhangzeshan/article/details/102568239 先贴上代码在进行说明 <?php /** * 通过同步的写法 实现异步的操作 * 协程组件 redis */ $http = new swoole_http_server("0.0.0.0",9501); $http->on('request',function ($request,$response){ //获取redis的数据 输出到浏览器 $redis = new Swoole\Coroutine\Redis(); $redis->connect("127.0.0.1",6379); //将请求连接的 get参数的值 获取redis中key对应的value $value = $redis->get($request->get['a']); //配置header头信息 $response->header("Content-Type","text/plain"); //获取之后 返回给客户端

go的编程哲学和设计理念

假装没事ソ 提交于 2019-12-13 00:56:42
go语言是互联网时代的语言,融合了众多互联网时代程序设计的特征。 并行与分布式支持。多核化和集群化是互联网时代的典型特征。 并发执行的“执行体” 执行体是个抽象的概念,在操作系统层面有多个概念与之对应,如操作系统自己掌管的进程(process)、进程内的线程(thread)以及进程内的协程 (coroutine,也叫轻量级线程)。多数语言在语法层面并不直接支持协程,而通过库的方式支持的协程的功能也并不完整,比如仅仅提供协程的创建、销毁与切换等能力。如果在这样的协程中调用一个同步IO操作,比如网络通信、本地文件读写,都会阻塞其他的并发执行协程,从而无法真正达到协程本身期望达到的目标。 Go语言在语言级别支持协程,叫goroutine。Go语言标准库提供的所有系统调用(syscall)操作,当然也包括所有同步IO操作,都会出让CPU给其他goroutine,这让事情变得非常简单。 go语言异步程序示例: func run(arg string) { // ... } func main() { go run("test") ... } 关于进程、线程、协程的区别可以参考如下几篇文章: 谈谈并发编程中的协程 一个“蝇量级” C 语言协程库 编程中的进程、线程、协程、同步、异步、回调 执行体间的通信 执行体间通信的方式: 执行体之间的互斥与同步 执行体之间的消息传递 执行体之间的互斥与同步

蚂蚁金服开源 MOSN 核心概念解析

扶醉桌前 提交于 2019-12-12 13:17:48
【推荐】2019 Java 开发者跳槽指南.pdf(吐血整理) >>> 前言 MOSN 是一款使用 Go 语言开发的 Service Mesh 数据平面代理,2018 年 7 月由蚂蚁金服开源,开源地址 https://github.com/sofastack/sofa-mosn ,MOSN 旨在为服务提供分布式、模块化、可观察和智能化的代理能力。MOSN 是 Modular Observable Smart Network 的简称。MOSN 可以与任何支持 xDS API 的 Service Mesh 集成,亦可以作为独立的四、七层负载均衡使用。未来 MOSN 将支持更多云原生场景,并支持 Nginx 的核心转发功能。 本文根据蚂蚁金服烈元 2019 年 11 月 30 日在 Gopher China Meetup 北京站上的分享整理而成, 查看分享回顾 ,同时本文已更新到 MOSN 官方文档 上。 MOSN 核心概念 MOSN 主要划分为如下模块,包括了网络代理具备的基础能力,也包含了 xDS 等云原生能力。 xDS(UDPA)支持 MOSN 支持云原生 统一数据面 API(UDPA) ,支持全动态配置更新。 xDS 是 Envoy 创建的一个关键概念,它是一类发现服务的统称,其包括如下几类: CDS:Cluster Discovery Service EDS:Endpoint

DIL全局解释锁

不问归期 提交于 2019-12-11 22:56:33
目录 DIL全局解释锁 一、介绍 二、使用多线程提高效率 三、协程 DIL全局解释锁 一、介绍 GIL本质就是一把互斥锁,既然是互斥锁,所有互斥锁的本质都一样,都是将并发运行变成串行,以此来控制同一时间内共享数据只能被一个任务所修改,进而保证数据安全 保护不同的数据安全,就应该加不同的锁 GIL全局解释器锁的优缺点 优点 保证数据的安全 缺点 单个进程下,开启多个线程,牺牲执行效率,无法实现并行,只能实现并发 import time from threading import Thread n = 100 def task(): global n m = n time.sleep(3) n = m - 1 if __name__ == '__main__': list1 = [] for line in range(10): t = Thread(target=task) t.start() list1.append(t) for t in list1: t.join() print(n) # 99 二、使用多线程提高效率 """ 分析: 我们有四个任务需要处理,处理方式肯定是要玩出并发的效果,解决方案可以是: 方案一:开启四个进程 方案二:一个进程下,开启四个线程 单核情况下,分析结果:   如果四个任务是计算密集型,没有多核来并行计算,方案一徒增了创建进程的开销,方案二胜  

IO框架:asyncio 下篇

a 夏天 提交于 2019-12-11 15:26:26
动态添加协程 在实战之前,我们要先了解下在asyncio中如何将协程态添加到事件循环中的。这是前提。 如何实现呢,有两种方法: 主线程是 同步 的 import time import asyncio from queue import Queue from threading import Thread def start_loop(loop): # 一个在后台永远运行的事件循环 asyncio.set_event_loop(loop) loop.run_forever() def do_sleep(x, queue, msg=""): time.sleep(x) queue.put(msg) queue = Queue() new_loop = asyncio.new_event_loop() # 定义一个线程,并传入一个事件循环对象 t = Thread(target=start_loop, args=(new_loop,)) t.start() print(time.ctime()) # 动态添加两个协程 # 这种方法,在主线程是同步的 new_loop.call_soon_threadsafe(do_sleep, 6, queue, "第一个") new_loop.call_soon_threadsafe(do_sleep, 3, queue, "第二个") while