Redis(三)

为什么单线程的Redis这么快?

事实上Redis并不是单线程的,我们通常说的单线程是指Redis的网络IO和键值对的读写是由一个线程来完成的,这也是Redis对外提供键值存储服务的主要流程。但Redis的其他功能,比如说持久化,异步删除,集群数据同步等,其实是由额外的线程执行的。

为什么用单线程?

日常中我们会听到一个说法“使用多线程,可以增加系统吞吐率,或是可以增加系统扩展性。”对于一个多线程的系统来说,在有合理的资源分配的情况下,可以增加系统中的处理请求操作的资源实体,进而提升系统能够同时处理的请求数,即吞吐率。在这里插入图片描述
但是,如果没有良好的系统设计,我们实际得到的结果,其实和右图展示的一模一样。刚开始增加线程数时,系统吞吐率会增加,但是,再进一步增加线程时,系统吞吐率增长迟缓,有时甚至还会出现下降的情况。
出现这种情况的原因就在于,系统中通常会存在被多线程同时访问的共享资源,比如一个共享的数据结构。当有多个线程要修改这个资源时,为了保护资源的正确性,就需要额外的机制来保证,而这个额外的机制,就会带来额外的开销。
并发访问控制一直时多线程开发中的一个难点问题,如果没有精细的设计,比如说妹纸时简单地采用一个粗粒度互斥锁,就会出现不理想的结果:即使增加线程,大部分线程也在等待获取访问共享资源的互斥锁,并行变串行,系统吞吐率并没有随着线程的增加而增加。
而且,采用多线程开发一般会引入同步原语来保护共享资源的并发访问,这也会降低系统代码的易调试性和可维护性。为了避免这些问题,Redis采用单线程模式。

为什么Redis这么快?

一方面,Redis的大部分操作在内存上完成,加上它采用的高效的数据结构,例如哈希表(O(1))和跳表(多级索引),这是它实现高性能的一个重要原因。另一方面,就是Redis采用了多路复用机制,使其在网络IO操作中能并发处理大量的客户端请求,实现高吞吐率。

多路复用机制

这就需要说到网络操作的基本IO模型和潜在的阻塞点。毕竟,Redis采用单线程进行IO,如果线程被阻塞了就,就无法多路复用了。以SimpleKV为例子,为了处理一个Get请求,需要监听客户端请求(bind/listen),和客户端建立连接(accept),从socket中读取请求(recv),解析客户端发送请求(parse),根据请求类型读取键值数据(get),最后给客户端返回结果,即向socket中写回数据(send)。在这里插入图片描述
但是,在这里的网络IO操作中,有潜在的阻塞点,分别是accept()和recv()。当redis监听到一个客户端有连接请求,但一直未能建立其连接的时候,会阻塞在accept()函数这里,导致其他客户端无法和redis建立起连接。类似的,当Redis通过recv()从一个客户端读取数据时,如果数据一直没有达到redis也会一直阻塞在recv()。这就导致redis整个线程阻塞,无法处理其他的客户端请求,效率很低。不过,幸运的是socket网络模型本身支持非阻塞模式。

非阻塞模式

Socket网络模型的非阻塞模式设置,主要体现在三个关键的函数调用上,如果想要使用socket非阻塞模式,就必须要了解这三个函数的调用返回类型和设置模式。
在socket模型中,不同的操作调用后会返回不同的套接字类型。socket()方法会返回主动套接字,然后调用listen()方法,将主动套接字转化为监听套接字,此时可以监听赖在客户端的连接请求。最后,调用accept()方法接受达到的客户端连接,并返回已连接套接字。在这里插入图片描述
针对监听套接字,我们可以设置非阻塞模式:当Redis吊桶accept()但一直未有连接请求到达时,Redis线程可以返回处理其他操作,而不是一直等待。但是,要注意调用accept()时,已经存在监听套接字了。虽然Redis线程可以不用继续等待,但是总得有机制继续在监听套接字上等待后续连接请求,并在有请求时同志Redis。类似的,我们也可以针对已连接的套接字设置非阻塞模式:Redis调用recv()后,如果已连接套接字上一直没有数据到达,Redis线程同样也可以返回处理其他操作。我也

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值