概述
现行的软件架构主要有两种:单进程多线程(如:memcached、redis、mongodb等)和多进程单线程(nginx、node)。
单进程多线程的主要特点:
- 快:线程比进程轻量,它的切换开销要少很多。进程相当于函数间切换,每个函数拥有自己的变量;线程相当于一个函数内的子函数切换,它们拥有相同的全局变量。
- 灵活: 程序逻辑和控制方式简单,但是锁和全局变量同步比较麻烦。
- 稳定性不高: 由于只有一个进程,其内部任何线程出现问题都有可能造成进程挂掉,造成不可用。
- 性能天花板:线程和主程序受限2G地址空间;当线程到一定数量后,即使增加cpu也不能提升性能。
多进程单线程的主要特点:
- 高性能:没有频繁创建和切换线程的开销,可以在高并发的情况下保持低内存占用;可以根据CPU的数量增加进程数。
- 线程安全:没有必要对变量进行加锁解锁的操作
- 异步非阻塞:通过异步I/O可以让cpu在I/O等待的时间内去执行其他操作,实现程序运行的非阻塞
- 性能天花板:进程间的调度开销大、控制复杂;如果需要跨进程通信,传输数据不能太大。
事实上异步通过信号量、消息等方式早就存在操作系统底层,但是一直没有能在高级语言中推广使用。
Linux Unix提供了epoll方便了高级语言的异步设计。epoll可以理解为event poll,不同于忙轮询和无差别轮询,epoll只会把哪个流发生了怎样的I/O事件通知我们;libevent和libev都是对epoll的封装,nginx自己实现了对epoll的封装。
浏览器
在支持html5的浏览器里,可以使用webworker来将一些耗时的计算丢入worker进程中执行,这样主进程就不会阻塞,用户也就不会有卡顿的感觉了。
worker