FWQ
Redis缓存IO模型的演进教程示例精讲
Redis缓存IO模型的演进教程示例精讲 0浏览 收藏 对于一个数据库开发者来说,牢固扎实的基础是十分重要的,golang学习网就来带大家一点点的掌握基础知识点。今天本篇文章带大家了解《Redis缓存IO模型的演进教程示例精讲》,主要介绍了redisIO模型、演进,希望对大家的知识积累有所帮助,快点收藏起来吧,否则需要时就找不到了! 然而随着时间的推移,单线程越来越不满足一些应用场景了,比如针对大key删除会造成主线程阻塞的问题,redis4.0出了一个异步线程。 针对单线程由于无法利用多核cpu的特性而导致无法满足更高的并发,redis6.0也推出了多线程模式。所以说redis是单线程越来越不准确了。 事件模型 redis本身是个事件驱动程序,通过监听文件事件和时间事件来完成相应的功能。其中文件事件其实就是对socket的抽象,把一个个socket事件抽象成文件事件,redis基于Reactor模式开发了自己的网络事件处理器。那么Reactor模式是什么? 通信 思考一个问题,我们的服务器是如何收到我们的数据的?首先双方先要建立TCP连接,连接建立以后,就可以收发数据了。发送方向socket的缓冲区发送数据,等待系统从缓冲区把数据取走,然后通过网卡把数据发出去,接收方的网卡在收到数据之后,会把数据copy到socket的缓冲区,然后等待应用程序来取,这是大概的发收数据流程。 copy数据的开销 因为涉及到系统调用,整个过程可以发现一份数据需要先从用户态拷贝到内核态的socket,然后又要从内核态的socket拷贝到用户态的进程中去,这就是数据拷贝的开销。 数据怎么知道发给哪个socket 内核维护的socket那么多,网卡过来的数据怎么知道投递给哪个socket? 答案是端口,socket是一个四元组: ip(client)+ port(client)+ip(server)+port(server) 注意千万不要说一台机器的理论最大并发是65535个,除了端口,还有ip,应该是端口数*ip数 这也是为什么一台电脑可以同时打开多个软件的原因。 socket的数据怎么通知程序来取 当数据已经从网卡copy到了对应的socket缓冲区中,怎么通知程序来取?假如socket数据还没到达,这时程序在干嘛?这里其实涉及到cpu对进程的调度的问题。从cpu的角度来看,进程存在运行态、就绪态、阻塞态。 就绪态:进程等待被执行,资源都已经准备好了,剩下的就等待cpu的调度了。 运行态:正在运行的进程,cpu正在调度的进程。 阻塞态:因为某些情况导致阻塞,不占有cpu,正在等待某些事件的完成。 当存在多个运行态的进程时,由于cpu的时间片技术,运行态的进程都会被cpu执行一段时间,看着好似同时运行一样,这就是所谓的并发。当我们创建一个socket连接时,它大概会这样: sockfd = socket(AF_INET,…