剑指“CPU飙高”问题

一、什么是cpu飙高?

一般指程序运行时cpu占用率过高
  linux系统中,我们使用top命令,会看到正在运行进程的cpu使用率等,同时在最上面也会看到总的cpu使用率,当总的cpu使用率过高,如果有运维监控平台,则一般我们会设置阈值大于80%就会发生报警。

一般来讲,我们说的cpu飙高指的是系统总的cpu高。我们会看到有用户进程使用的cpu使用率可能会300%乃至600%等,这时候如果是正常的cpu密集型计算导致,其实我们来看系统总的cpu使用率统计,它可能并不高,所以这种情况我们可认为是正常的(只有导致系统cpu整体飙高,我们这时候才认为不正常、当然先决条件是要排除一些客观因素后)。
  可参考下图,红色框选出来的即为总的cpu使用率。
在这里插入图片描述
图(一) 上图是top命令下的界面展示

二、为什么会cpu飙高?

cpu密集型计算
   针对于程序的执行,对硬件资源的使用情况,我们可以分为cpu密集型计算和io密集型计算。对于一些cpu密集型计算,如果对cpu的压榨特别狠,则会产生cpu飙高。
对于web服务访问量增大就有可能cpu飙高
   如果某一时刻有很多用户来访问某一web服务,需要处理大量请求而导致cpu飙高。
图 (二) 上图是个80个用户并发访问的loadrunner图形化状态展示
图 (二) 上图是个80个用户并发访问的loadrunner图形化状态展示
在这里插入图片描述

图(三) 上图是nmon工具对后台服务器的监控界面 如图三所示,其中cpu使用率高达95%(cpu utillisation中
User%指代的是用户态下(也就是目态)cpu使用率,Sys%指代的是管态下,cpu的使用率),这是在80个用户并发的情况下达到的,需要查明原因是因为用户访问量上去正常导致,还是程序里面有不合理的地方而导致,本图中所示是程序里有不合理的地方而导致。

不合理的定时任务资源调度也会导致cpu飙高

程序中某一位置代码写的不合理而导致的cpu飙高:
  比如:
   使用hashMap容器计算处理一些数据时,出现了一些不合理的操作。
   多线程任务时,线程发生死锁。
   不合理的多线程高并发程序。
   在调用数据库查询时,极短的时间内频繁调用模糊查询(这时候不仅对数据库有资源占有压力,也对应用服务器有一定的资源占有压力)。
   低版本jdk下易发生(有些写法低版本jdk是不适用的,因为有些操作,它的底层没有像高版本被优化过)。

三、如何躺平式处理cpu飙高问题

不合理程序导致的cpu飙高
1、定位导致cpu飙高的源头进程
  可以通过使用top命令看到cpu最高的进程号,观察其属于哪个应用。
  如图一所示,可以看到cpu使用率排第二的是一个java程序,如果java程序cpu使用率很高,则可以进一步追踪进去,观察它是由于哪个线程导致的cpu飙高。
top直接使用top命令
2、定位导致cpu飙高的线程
  依然使用top命令,通过高cpu的应用进程号查到该进程下那些线程cpu占用率最高。
top -Hp pid 可以查看某个进程的线程信息(pid为进程号),此linux命令,其中参数H指展示线程信息,p指代展示对应的哪个进程号。
3、查看导致cpu飙高的线程堆栈
  使用jstack命令查看cpu占用率高的堆栈信息,这时候,如果是有问题的程序,堆栈信息里面就已经会有所体现了。
  另外,jstack命令属于java sun jdk的tools工具命令,需要在linux中配置jdk环境变量才可以使用,或者直接用jstack命令的全路径名执行。
先将第一二步进程对应的使用率最高的线程号转换为16进制,留待接下来的命令使用,使用 printf "%x\n" pid转换,例如:printf "%x\n" 25553,其中25553就是线程号(25553转换为16进制是63d1)。接下来使用 jstack 25556 | grep 63d1 -A 50 ,(25556是使cpu飙高的25553线程所属的进程号,63d1是线程号25553转为16进制后的值)使用此命令后,基本上有问题就可以看出来了,包括代码原因导致的异常显示,或者线程死锁,阻塞等。
4、找到异常堆栈分析原因
  找到异常堆栈后,查看是否有自己程序中开发的数据的代码行,直接去应用程序源码的对应位置分析该处是否写的有误。
一般在第三步中使用jstack命令后,出现在堆栈信息中的程序代码很大概率是问题代码,可以到具体代码行去排查和看了,如果实在发现不了问题,可以直接换写法看结果是否还是如此,或者猜测法猜测。
5、由原因进行程序优化和问题修复或改进
  根据排查出的问题,进行代码优化。
如果出现的是tps瓶颈或者吞吐量问题,那么这时候就可以考虑jvm层进行优化一波了,具体优化原理,可移步作者的jvm专栏进行查看。(一般需要调优垃圾回收器,堆参数,gc回收阈值等,还可以调整解释和编译执行的阈值等)
web服务因访问量增多而导致的cpu飙高
   web服务因访问量增多而导致的cpu飙高是很正常的cpu飙高,这时候我们可以考虑增加硬件资源,或者做集群来分流,更倾向于高并发导致。
  初期开发完毕后,在性能测试以后,肯定要进行分析,这时候就是探究是因为什么原因导致的cpu升高了,可以把并发慢慢提上去,如果初期小并发就出现问题了,那很大可能就是代码有问题了!
躺平式
  其实cpu飙高问题很常见,不要碰到cpu飙高就畏之如虎,其实排查解决起来很简单,前置条件理清,可能发生的大的原因其实就是以上所列出来那些,只要按照作者说的那个步骤,基本问题不大就处理掉了。
  当然,也有一些极端情况,如cpu温度过高等导致cpu飙高及其它…,这种情况我们基本碰不到的。   jstack是常用的命令,一般通过它就可以排查出问题了,我们也可以设置服务器运行时的jvm参数,设置记录gc日志和oom信息,由此在发生相关异常情况时即可快速定位。也可在使用jstat命令查看gc信息,jstat命令在这里不做细说。
在这里贴出来个jvm配置参数

 //weblogic  setDominEnv.shJAVA_OPTIONS="-Xms3072 -Xmx3072m -XX:+UseG1GC -xloggc:/home/weblogic/gclog/gc.log -XX:+HeapDumpOnOutOfMemoryError -XX:HeapDumpPath=/home/weblogic/oom"//tomcat catalina.shJAVA_OPTS="-Xms3072 -Xmx3072m -XX:+UseG1GC -xloggc:/home/weblogic/gclog/gc.log -XX:+HeapDumpOnOutOfMemoryError -XX:HeapDumpPath=/home/weblogic/oom"

这些参数是jvm参数,与服务器中间件无关,所以参数不用做更改,只是配置的位置和脚本变量根据不同的中间件有所不一样而已。其中-Xms是最小堆空间,-Xmx是最大堆空间,weblogic最大最小堆空间配置一样即可,tomcat最大最小堆空间可根据实际情况配置。-xlogGc是gc日志记录的地方,-XX:+heapDumpPath是堆溢出时导出堆文件的目录路径

另:jvm可被监控,只要开启监控端口即可,另外客户端启动监控时要注意该jdk版本是否和被监控jdk版本一致或者稍大。小版本jdk jvisualvm工具不可监控大版本jvm。java的jdk包下的jdk目录bin目录下有一些jdk 工具,jvisualvm是其中一个。可通过jvm监控,观察服务运行jvm内部的平稳性,对于jvm的平稳性是有要求的,不宜极大波动(可类比天地板)(频繁)。

//jvm监控端口开放配置,如上,也配置在jvm参数中即可"-Dcom.sun.management.jmxremote.port=8999 -Dcom.sun.management.jmxremote.ssl=false -Dcom.sun.management.jmxremote.authenticate=false "

四、一个栗子

栗子概要:高并发下大量模糊查询的cpu飙高。

环境:
oracle数据库
webloigc应用容器。
  ……
  以前,有一次做完一个项目,信心满满,业务测试后觉得一点问题也没有,可以投产了。
  但是就在投产前的三个星期,进行投产前的最后一步——性能测试的时候,出问题了!
  只有10并发的访问量,cpu使用率居然超过了80%,纳尼?这是什么鬼,首先检查了压力测试录制的c脚本,发现 脚本里面是需要点击多条件联合查询页,这个里面有模糊查询(后置模糊是可以索引命中的),对于主检索字段都建了索引,基本可以优化的都优化了,最后发现忘了一步,对于多条件联合检索,是需要创建联合索引才可以,而且要包括所有的会联合的字段。
  最后发现做了此种操作后,还是不行,虽然比以前好多了,但是并发量稍微上去,cpu还是容易飙高,定位后还是模糊查询导致,这时候进行了默认首页数据缓存,彻底解决了这个联合查询页默认点击后的cpu飙高问题。
稍微解释一下:如果模糊查询过慢,会导致请求线程处理等待等,这时候频繁访问,老线程得不到释放,其实是很容易让cpu升起来的,因为每个线程都会占用一定的资源,尤其是在并发下。

上面的这个栗子,只是个简单的栗子,但是说明什么?说明出现cpu飙高问题,需要在整体环境下进行考虑和排查,而不能仅仅局限于程序运行的服务器环境和程序本身,整体环境下考虑才能更完整、更容易找到真正的cpu飙高原因,原因找到了,剩下的其实就是确定优化方案,这一步就相对容易了。

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

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

相关文章

【Linux】理解文件系统

需要云服务器等云产品来学习Linux的同学可以移步/–>腾讯云<–/官网&#xff0c;轻量型云服务器低至112元/年&#xff0c;优惠多多。&#xff08;联系我有折扣哦&#xff09; 文章目录 1. 了解磁盘1.1 磁盘的物理结构1.2 磁盘的逻辑结构1.3 磁盘的存储结构 2. 文件系统2.…

2023年12月编程语言排行榜

TIOBE Index for December 2023 December Headline: C# on its way to become programming language of the year 2023 2023年12月的TIOBE指数&#xff1a;12月头条:c#将成为2023年最佳编程语言 Yes, I know, we have been here before. At the end of 2022, it looked like …

全局异常和自定义异常处理

全局异常GlobalException.java&#xff0c;basePackages&#xff1a;controller层所在的包全路径 import com.guet.score_management_system.common.domian.AjaxResult; import org.springframework.web.bind.annotation.ControllerAdvice; import org.springframework.web.bi…

电脑怎么设置代理IP上网?如何隐藏自己电脑的真实IP?

在现代互联网中&#xff0c;代理IP已成为许多用户保护隐私和上网安全的重要手段。通过设置代理IP&#xff0c;用户可以隐藏自己的真实IP地址&#xff0c;提高上网的安全性&#xff0c;同时保护个人信息不被泄露。本文将详细介绍如何设置代理IP上网以及如何隐藏电脑的真实IP地址…

Vue Tinymce富文本组件添加自定义字体项

实现效果如下&#xff1a; Tinymce 组件进行字体设置 设置完后&#xff0c;就可以使用自定义的字体了。

Spring Boot整合 EasyExcel 实现复杂 Excel 表格的导入与导出功能

文章目录 1. 简介2. 引入依赖3. 导入功能实现3.1 创建实体类3.2 编写导入 Controller3.3 编写导入页面 4. 导出功能实现4.1 编写导出 Controller4.2 编写导出页面 5. 启动应用 &#x1f388;个人主页&#xff1a;程序员 小侯 &#x1f390;CSDN新晋作者 &#x1f389;欢迎 &…

你好2024!

大家好&#xff0c;我是小悟 2024年1月1日&#xff0c;新年的第一天&#xff0c;阳光明媚&#xff0c;空气中弥漫着希望和新的开始的气息。在这个特别的日子里&#xff0c;大家纷纷走出家门&#xff0c;迎接新年的到来。 街道上&#xff0c;熙熙攘攘的人群中&#xff0c;有孩…

【动态管理日志】Spring Boot 实现 热插拔 AOP,非常实用!

现在有这么一个需求&#xff1a;就是我们日志的开与关是交给使用人员来控制的&#xff0c;而不是由我们开发人员固定写死的。大家都知道可以用aop来实现日志管理&#xff0c;但是如何动态的来实现日志管理呢&#xff1f;aop源码中的实现逻辑中有这么一个步骤&#xff0c;就是会…

将学习自动化测试时的医药管理信息系统项目用idea运行

将学习自动化测试时的医药管理信息系统项目用idea运行 背景 学习自动化测试的时候老师的运行方式是把医药管理信息系统项目打包成war包后再放到tomcat的webapp中去运行&#xff0c;于是我想着用idea运行会方便点&#xff0c;现在记录下步骤方便以后查找最开始没有查阅资料&am…

蓝牙物联网灯控设计方案

蓝牙技术是当前应用最广泛的无线通信技术之一&#xff0c;工作在全球通用的 2.4GHZ 的ISM 频段。蓝牙的工作距离约为 100 米&#xff0c;具有一定的穿透性&#xff0c;没有方向限制。具有低成本、抗干扰能力强、传输质量高、低功耗等特点。蓝牙技术组网比较简单&#xff0c;无需…

【 YOLOv5】目标检测 YOLOv5 开源代码项目调试与讲解实战(3)-训练yolov5模型(本地)

训练yolov5模型&#xff08;本地&#xff09; 训练文件 train.py训练如下图 一些参数的设置weights:对于weight参数&#xff0c;可以往Default参数中填入的参数有 cfg&#xff1a;&#xff08;缩写&#xff09;cfg参数可以选择的网络模型 data对于data hyp 超参数epochs 训练多…

托管在亚马逊云科技的向量数据库MyScale如何借助AWS基础设施构建稳定高效的云数据库

MyScale是一款完全托管于亚马逊云科技&#xff0c;支持SQL的高效向量数据库。MyScale的优势在于&#xff0c;它在提供与专用向量数据库相匹敌甚至优于的性能的同时&#xff0c;还支持完整的SQL语法。以下内容&#xff0c;将阐述MyScale是如何借助亚马逊云科技的基础设施&#x…

张量操作与线性回归

一、张量的操作&#xff1a;拼接、切分、索引和变换 &#xff08;1&#xff09;张量拼接与切分 1.1 torch.cat() 功能&#xff1a;将张量按维度dim进行拼接 • tensors: 张量序列 • dim : 要拼接的维度 torch.cat(tensors, dim0, outNone)函数用于沿着指定维度dim将多个张量…

simulink代码生成(六)——多级中断的配置

假如系统中存在多个中断&#xff0c;需要合理的配置中断的优先级与中断向量表&#xff1b;在代码生成中&#xff0c;要与中断向量表对应&#xff1b;中断相关的知识参照博客&#xff1a; DSP28335学习——中断向量表的初始化_中断向量表什么时候初始化-CSDN博客 F28335中断系…

【计算机毕业设计】SSM汽车维修预约平台

项目介绍 本项目分为前后台&#xff0c;前台为普通用户登录&#xff0c;后台为管理员登录&#xff1b; 管理员角色&#xff1a; 管理员登录,新增管理员信息,查看管理员信息,查询管理员信息,查看用户信息列表,查询用户信息,新增新闻公告,查看新闻公告,查询新闻公告,新增配件类…

matplotlib范围曲线简例

想在画&#xff08;平均&#xff09;loss 曲线时顺便表示方差&#xff0c;即每一个 epoch 的平均 loss 用 plot 画曲线&#xff0c;而在曲线周围用一个浅色区域表示方差。效果&#xff1a; 参考 [1-3]&#xff0c;用到 matplotlib.pyplot.fill_between 函数。为显示对浅色区及…

不吹不黑,辩证看待开发者是否需要入坑鸿蒙

前言 自打华为2019年发布鸿蒙操作系统以来&#xff0c;网上各种声音百家争鸣。尤其是2023年发布会公布的鸿蒙4.0宣称不再支持Android&#xff0c;更激烈的讨论随之而来。 本文没有宏大的叙事&#xff0c;只有基于现实的考量。 通过本文&#xff0c;你将了解到&#xff1a; Har…

Python列表推导式(for表达式)及用法

for 表达式&#xff08;列表推导式&#xff09;用于利用其他区间、元组、列表等可迭代对象创建新的列表。 for 表达式的语法格式如下&#xff1a; [表达式 for 循环计数器 in 可迭代对象] 从上面的语法格式可以看出&#xff0c;for 表达式与普通 for 循环的区别有以下两点&a…

什么是JavaScript

文章目录 一、❄️什么是JavaScript&#xff1f;二、❄️JavaScript的特点三、❄️JavaScript的组成&#x1f9eb;1、核心&#xff08;ECMAScript&#xff09;&#x1f9ff;2、文档对象模型&#xff08;DOM&#xff09;&#x1f94f;3、浏览器对象模型&#xff08;BOM&#xff…

深入理解MySQL索引底层数据结构

听课问题(听完课自己查资料) 什么是二叉树 二叉树是怎么存储数据的一个链表是一个集合的数据结构 List是怎么便利找到指定下标元素为什么会快&#xff1f;什么是红黑树 红黑树是怎么存储数据的什么是B TREE 是怎么存储数据的什么是BTREE 是怎么存储数据的 疑惑答案 a. 二叉树…