php 提高吞吐量,如何提高网站的吞吐量

吞吐量定义

百科

吞吐量是指对网络、设备、端口、虚电路或其他设施,单位时间内成功地传送数据的数量(以比特、字节、分组等测量)。

以上的定义比较宽泛,定义到网站或者接口的吞吐量是这样的:吞吐量是指系统在单位时间内处理请求的数量。这里有一个注意点就是单位时间内,对于网站的吞吐量这个单位时间一般定义为1秒,也就是说网站在一秒之内能处理多少http(https/tcp)请求。与吞吐量对应的衡量网站性能的还有响应时间、并发数、QPS每秒查询率。

响应时间是一个系统最重要的指标之一,它的数值大小直接反应了系统的快慢。响应时间是指执行一个请求从开始到最后收到响应数据所花费的总体时间。

并发数是指系统同时能处理的请求数量,这个也是反应了系统的负载能力。

每秒查询率(QPS)是对一个特定的查询服务器在规定时间内所处理流量多少的衡量标准,在因特网上,作为域名系统服务器的机器的性能经常用每秒查询率来衡量。对应fetches/sec,即每秒的响应请求数,也即是最大吞吐能力。

我们以高速收费站为例子也许更直观一些,吞吐量就是一天之内通过的车辆数,响应时间就是车速,并发数就是高速上同时奔跑的汽车数。由此可见其实以上几个指标是有内在联系的。比如:响应时间缩短,在一定程度上可以提高吞吐量。

其实以上几个指标主要反映了两个概念:

系统在单位时间之内能做多少事情

系统做一件事情需要的时间

提高吞吐量

以下场景都是在假设程序不发生异常的情况下

服务器(进程)级别

服务器级别增加网站吞吐量也是诸多措施中最容易并且是效果最好的,如果一个网站能通过增加少量的服务器来提高吞吐量,菜菜觉得是应该优先采用的。毕竟一台服务器的费用相比较一个程序员费用来说要低的多。但是有一个前提,就是你的服务器是系统的瓶颈,网站系统之后的其他系统并非瓶颈。如果你的系统的瓶颈在DB或者其他服务,盲目的增加服务器并不能解决你的问题。

通过增加服务器来解决你的网站瓶颈,意味着你的网站需要做负载均衡,如果没有运维相关人员,你可能还得需要研究负载均衡的方案,比如LVS,Nginx,F5等。我曾经面试过很多入道不久的同学,就提高吞吐量问题,如果没有回答上用负载均衡方案的基本都pass了,不要说别的,这个方案就是一个基础,就好比学习一个语言,你连最基本的语法都不会,我凭什么让你通过。有喷的同学可以留言哦

其实现在很多静态文件采用CDN,本质上也可以认为是增加服务器的策略

线程级别

当一个请求到达服务器并且正确的被服务器接收之后,最终执行这个请求的载体是一个线程。当一个线程被cpu载入执行其指令的时候,在同步的状态下,当前线程会阻塞在那里等待cpu结果,如果cpu执行的是比较慢的IO操作,线程会一直被阻塞闲置很长时间,这里的很长是对比cpu的速度而言,如果你想有一个直观的速度对比,可以去查看菜菜以前的文章:

高并发下为什么更喜欢进程内缓存

当一个新的请求到来的时候,如果没有新的线程去领取这个任务并执行,要么会发生异常,要么创建新的线程。线程是一种很稀缺的资源,不可能无限制的创建。这种情况下我们就要把线程这种资源充分利用起来,不要让线程停下来。这也是程序推荐采用异步的原因,试想,一个线程不停的在工作,遇到比较慢的IO不会去等待结果,而是接着处理下一个请求,当IO的结果返回来得到通知的时候,线程再去取IO结果,岂不是能在相同时间内处理更多的请求。

程序异步化(非阻塞)会明显提高系统的吞吐量,但是响应时间可能会稍微变大

还有一点,尽量减少线程上线文在cpu的切换,因为线程上线文切换的成本也是比较大的,在线程切换的时候,cpu需要把当前线程的上下文信息记录下来用以下次调用的时候使用,然后把新线程的上下文信息载入然后执行。这个过程相对于cpu的执行速度而言,要慢很多。

不要拿Golang反驳以上观点,golang的协程虽然是用户级别比线程更小的载体,但是最终和Cpu进行交互的还是线程。

Cpu级别

在讲cpu级别之前,如果有一定的网络模型的基础,也许会好一些。这里大体阐述一下,现代操作系统都采用虚拟寻址的方式,它的寻址空间(虚拟存储空间)为4G(2的32次方)。操作系统将虚拟空间分为两类:内核空间和用户空间。内核空间独立于用户空间,有访问受保护的内存空间、IO设备的权限(所有的用户空间共享)。用户空间就是我们的应用程序运行的空间,其实用户空间并没有操作各种IO设备的权限,像我们平时读取一个文件,本质上是委托内核空间去执行读取指令的,内核空间读取到数据之后再把数据复制到程序运行的空间,最后应用程序再把数据返回调用方。

2d4fce657780a11e0df0ee107500dca5.gif

image

通过上图大体可以看出,内核会为每个I/O设备维护一个buffer(同一个文件描述符读和写的buffer不同),应用程序发出一个IO操作的指令其实通过了内核空间和用户空间两个部分,并且发生了数据的复制操作。这个过程其实主要包含两个步骤:

用户进程发出操作指令并等待数据

内核把数据返回给用户进程(buffer的复制操作)

根据这两个操作的不同表现,所以IO模型有了同步阻塞,同步非阻塞,异步阻塞,异步非阻塞的概念,但是这里并非此文的重点,所以不在展开详细介绍。

利用cpu提高系统吞吐量主要目标是提高单位时间内cpu运行的指令数,避免cpu做一些无用功:

cpu负责把buffer的数据copy到应用程序空间,应用程序再把数据返回给调用方,假如这个过程发生的是一次Socket操作,应用程序在得到IO返回数据之后,还需要网卡把数据返回给client端,这个过程又需要把刚刚得到的buffer数据再次通过内核发送至网卡,通过网络传送出去。由此可见cpu把buffer数据copy到应用程序空间这个过程完全没有必要,在内核空间完全可以把buffer数据直接传输至网卡,这也是零拷贝技术要解决的问题。具体的零拷贝技术在这里不再展开。

不要让任何设备停下来,不要让任何设备做无用功

通过增加cpu的个数来增加吞吐量

网络传输级别

至于网络传输级别,由于协议大部分是Tcp/ip,所以在协议传输方面优化的手段比较少,但是应用程序级别协议可以选择压缩率更好的,比如采用grpc会比单纯的http协议要好很多,http2 要比http 1.1要好很多。另外一方面网卡尽量加大传输速率,比如千兆网卡要比百兆网卡速度更快。由于网络传输比较偏底层,所以人工干预的切入点会少很多。

最后总结

大部分程序员都是工作在应用层,针对应用级别代码能提高吞吐量的建议:

加大应用的进程数,增加并发数,特别在进程数是瓶颈的情况下

优化线程调用,尽量池化。

应用的代码异步化,特别是异步非阻塞式编程对于提高吞吐量效果特别明显

充分利用多核cpu优势,实现并行编程。

减少每个调用的响应时间,缩短调用链。例如通过加索引的方式来减少访问一次数据库的时间

搜索公众号:架构师修行之路,领取福利,获取更多精彩内容

有疑问加站长微信联系(非本文作者)

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/371584.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

ubuntu下如何查找某个文件的路径

1.whereis 文件名 特点:快速,但是是模糊查找,例如 找 #whereis mysql 它会把mysql,mysql.ini,mysql.*所在的目录都找出来. 2.find / -name 文件名 特点:准确,但速度慢,消耗资源大,例如我想找到PHP.ini的准确位置,就需要用 #find / -name php.ini 3.locate 文件名 强力推荐的方…

事件的学习

1.鼠标单击事件( onclick &#xff09;: onclick是鼠标单击事件&#xff0c;当在网页上单击鼠标时&#xff0c;就会发生该事件。同时onclick事件调用的程序块就会被执行&#xff0c;通常与按钮一起使用。 <!DOCTYPE HTML> <html> <head> <meta http-equiv…

使用您自己的规则在Eclipse中自定义PMD

PMD是非常好的Java代码扫描程序&#xff0c;可帮助您避免潜在的编程问题。 它可以轻松扩展以满足您的需求&#xff0c;并且本文将为您带来与JPA的Enumerated注释用法相关的自定义PMD规则的简单示例。 在继续阅读之前&#xff0c;您应该检查我以前的文章之一-JPA-Enumerated def…

切换oracle用户impdp,Oracle 12c pdb使用expdp/impdp导入导出

12c推出了可插拔数据库&#xff0c;在一个容器cdb中以多租户的形式同时存在多个数据库pdb。在为pdb做数据泵导入导出时和传统的数据库有少许不同。1&#xff0c;需要为pdb添加tansnames2&#xff0c;导入导出时需要在userid参数内指定其tansnames的值&#xff0c;比如 useridus…

搭建mysql集群,使用Percona XtraDB Cluster搭建

Percona XtraDB Cluster提供的特性有&#xff1a;1.同步复制&#xff0c;事务要么在所有节点提交或不提交。2.多主复制&#xff0c;可以在任意节点进行写操作。3.在从服务器上并行应用事件&#xff0c;真正意义上的并行复制。4.节点自动配置。5.数据一致性&#xff0c;不再是异…

使用NoSQL实现实体服务–第4部分:Java EE

现在&#xff0c;我已经准备好了框架式的合同优先型Web服务&#xff0c;并使用Ektorp和CouchDB创建了数据访问层 &#xff0c;是时候将它们连接到一个可以正常工作的实体服务中了 。 为此&#xff0c;我将使用Java EE和Glassfish 3.1。 值得注意的是&#xff0c;对于他的那种R&…

yii2之DetailView小部件

DetailView小部件用于展示单条数据记录&#xff0c;可配置属性很少&#xff0c;使用也很简单&#xff0c;直接贴代码&#xff0c;一看就懂&#xff01; yii小部件数据小部件DetailView的使用示例&#xff1a; <? DetailView::widget([model > $user,//模型对象&#xff…

克隆安装oracle,Oracle 之 Cloning $oracle_home (克隆安装oracle软件)

用途&#xff1a;Cloning an Oracle Home &#xff0c; 可以免去多台机器重复安装oracle软件1、停止相关进程[rootnode1 bin]# ./crsctl stop cluster -all2、打包 dbhome_1 目录[rootnode1 11.2.0]# cd /u01/app/oracle/product/11.2.0/[rootnode1 11.2.0]# tar -zcvpf db_1.b…

gitlab的安装和基本维护

基本介绍 GitLab是一个自托管的Git项目仓库&#xff0c;可以自己搭建个人代码管理的仓库&#xff0c;功能与github类似。 安装 操作系统&#xff1a;CentOS6.5 gitlab官网下载安装地址&#xff1a;https://about.gitlab.com/downloads/#centos6 1.安装依赖的包 yum install cur…

Spring配置文件和Java配置

我的上一个博客介绍了Spring 3.1的配置文件&#xff0c;并解释了使用它们的业务案例&#xff0c;并演示了它们在Spring XML配置文件中的用法。 但是&#xff0c;似乎很多开发人员更喜欢使用Spring的基于Java的应用程序配置&#xff0c;因此Spring设计了一种使用带有现有Configu…

php 删除单个文件大小,php删除指定大小的jpg文件

function actionZmdel(){//set_time_limit(0);$dir dirname(dirname(dirname(dirname(__FILE__))))./2012jxgwyimg;$dirarr scandir($dir);echo 正在删除...;foreach($dirarr as $subdir){if($subdir ! . && $subdir ! ..){$path $dir./.$subdir;$files glob($path…

2017寒假零基础学习Python系列之函数之 函数之定义可变参数

若想让函数接受任意个参数&#xff0c;就可以定义一个可变的参数&#xff1a; def fn(*args): print args fn() >>>() fn(1,2,5,6) >>>(1,2,5,6) 原理是Python解释器把传入的一组参数封装在一个tuple传递给可变参数&#xff0c;因此在函数内部&#xff0c;直…

在Windows上构建OpenJDK

通过做一些实验&#xff0c;我发现手头提供JDK源代码来进行一些更改&#xff0c;使用它等等通常很有用。因此&#xff0c;我决定下载并编译该野兽。 显然&#xff0c;这花了我一些时间&#xff0c;尽管我最初的想法是&#xff0c;它应该和运行make命令一样简单&#xff1a;&…

unity中怎么在InspectorI面板加LOGO

转载于:https://www.cnblogs.com/unitySPK/p/7278925.html

oracle stream 主键,oracle stream配置向导

1. Stream 的工作原理Stream 是Oracle Advanced Queue技术的一种扩展应用&#xff0c;这种技术最基本的原理就是收集事件&#xff0c;把时间保存在队列中&#xff0c;然后把这些事件发布给不同的订阅者。从DBA的角度来说&#xff0c;就是把捕获Oracle数据库产生的Redo日志&…

JavaScriptDOM 十四. Event DOM的属性

1 <!DOCTYPE html>2 <html>3 <head>4 <title></title>5 <script type"text/javascript">6 7 /*8 1. --------------- Event DOM 事件DOM 用户交互 ------------------9 当事件发生时, 执行JS功能代码10 11 常用…

五、创建Bean的三种方式

五、创建Bean的三种方式转载于:https://www.cnblogs.com/ljiwej/p/7280614.html

重写到边缘–充分利用它! 在GlassFish上!

现代应用程序开发的一个重要主题是重写。 自从Java Server Faces引入和Java EE 6中新的轻量级编程模型以来&#xff0c;您一直在努力使用漂亮&#xff0c;简单&#xff0c;可添加书签的URL。 PrettyFaces很久以来就一直存在&#xff0c;即使它在3.3.3版本中可以说是成熟的&…

php yii框架路由,yii框架路由配置

首先要在服务器配置(httpd.conf)中开启重写模块#开启重写模块&#xff0c;将其前面的#去掉LoadModule rewrite_module modules/mod_rewrite.so#Directory中允许覆盖开启## Possible values for the Options directive are "None", "All",# or any combinat…

前端面试总结二

一、响应式和自适应的区别&#xff1a; 联系(相同点)&#xff1a; 响应式设计(responsive design)和自适应设计(adaptive design)都是用来解决网页在不同分辨率的屏幕和设备上展示的一项技术(或者说一种方法)。 区别&#xff1a; 响应式设计&#xff1a;通过CSS Media Queries(…