当前位置: 首页 > news >正文

静海区网站建设推广手机参数查询网站

静海区网站建设推广,手机参数查询网站,网页制作与设计中什么是div,装饰工程造价【性能优化】安卓性能优化之CPU优化 CPU优化及常用工具原理与文章参考常用ADB常用原理、监控手段原理监控手段多线程并发解决耗时UI相关 常见场景排查CPU占用过高常用系统/开源分析工具AndroidStudio ProfilerSystraceBtracePerfettoTraceView和 Profile ANR相关ANR原理及常见场… 【性能优化】安卓性能优化之CPU优化 CPU优化及常用工具原理与文章参考常用ADB常用原理、监控手段原理监控手段多线程并发解决耗时UI相关 常见场景排查CPU占用过高常用系统/开源分析工具AndroidStudio ProfilerSystraceBtracePerfettoTraceView和 Profile ANR相关ANR原理及常见场景ANR/卡顿检测卡顿检测 CPU 优化案例 CPU优化及常用工具 原理与文章参考 编舞者、looper、JankStats方法 常用ADB 含义命令备注查看CPU状态adb shell top -H -d 1 -p pid -O cpu-O cpu 查看对应在那个核心 修改采样间隔为1s导出当前进程所有线程状态到tombstonedadb shell run-as kill -3 实际上是以一个异常状态导出了利用了墓碑机制查看进程的所有线程adb shell ps -Tgrep pid查看进程占用cpu情况adb shell dumpsys cpuinfogrep [进程名]查看进程内线程占用cpu的情况adb shell top -n 1 -d 0.5grep proc_ id获取设备cpu信息adb shell cat /proc/cpuinfo或者查看 /sys/devices/system/cpu 目录下的文件夹 常用原理、监控手段 原理 普通手机默认60帧刷新率相当于每帧16.6ms利用系统预留接口 对每个帧率/handler消息等 进行统计 监控手段 设置looperPrinter字节码插桩检测慢函数martix dokit编舞者获取frame帧率jetpack JankStats获取丢帧信息 多线程并发解决耗时 线程池/数量参考 CPU密集线程数设置为CPU核心数 1IO密集线程数设置为CPU核心数 * 2 UI相关 利用font stylecolor:rgb(77, 77, 77);IdelHandler/font对一些常用view进行预绘制通过排查布局减少过度绘制 常见场景 过度绘制频繁IO主线程耗时任务 排查CPU占用过高 规范线程命名定位线程抓取top数据查看具体哪个线程占用高cpu指标含义解释线程各参数详解 常用系统/开源分析工具 AndroidStudio Profiler 抓取CPU火焰图卡顿/ANR 主要监测主线程是否会出现耗时操作 Systrace 官方指令参考官方推荐指令 $ python systrace.py -o mynewtrace.html sched freq idle am wm gfx view binder_driver hal dalvik camera input res要求环境 python2.7 安装 python six 模块命令 : pip install six “No module named win32con” 问题安装相关 pip install pypiwin32 拉取到信息后用perfetto 打开即可 但是这个主要是针对系统的 对应用开发帮助不大分析自己应用可以用btrace Btrace 官方链接 Perfetto 官方-快速开始工具界面入门使用线程状态 TraceView和 Profile traceview官方参考traceview使用导出的日志分析使用DDMS查看 新版路径Sdk\tools\monitor.bat Incl Cpu Time方法在CPU中执行所有时间包含其调用的方法所消耗的时间Excl Cpu Time: 方法在CPU中执行的时间不包含其调用的方法所消耗的时间Incl Real Time方法运行消耗的所有时间包含子方法Excl Real Time方法运行消耗的时间不包含子方法Calls Recur Calls/Total 方法调用、递归次数重要指标防止死循环Cpu Time/Call 该方法平均占用 CPU 的时间重要指标可以看出单个方法占用CPU的平均时间但是要防止在个别调用处出现长时间占用然后被平均了Real Time/Call 平均执行时间包括切换、阻塞的时间重要指标可以看出单个方法执行的平均时间值但是要防止在个别调用处出现长时间调用然后被平均了 TraceView优势 可以精确埋点 Debug.startMethodTracing(sample);... Debug.stopMethodTracing();ANR相关 ANR原理及常见场景 原理 ANRApplication Not Responding的监测原理本质上是消息机制设定一个delay消息超时未被移除则触发ANR。具体逻辑处理都在system server端包括发送超时消息移除超时消息处理超时消息以及ANR弹框展示等对于app而言触发ANR的条件是主线程阻塞。 常见场景 Service ANR前台20s后台200sstartForeground超时10sBroadcast ANR前台10s后台60sInput ANR按键或触摸事件在5s内无响应ContentProvider ANR10s少见 ANR/卡顿检测 通过设置Looper的printer可以检测耗时WatchDog机制子线程发送消息自增休眠后检查参考ANR日志导出 // 安卓21以下有权限可以获取到 anr 日志 private FileObserver fileObserver null; void initialize(....){// 实例化FileObserver ,监控路径/data/anr/监听文件被写入fileObserver new FileObserver(/data/anr/, CLOSE_WRITE) {public void onEvent(int event, String path) {try {if (path ! null) {String filepath /data/anr/ path;// 写入的文件是否有关键字 “trace”if (filepath.contains(trace)) {// 处理anr异常handleAnr(filepath);}}} catch (Exception e) {XCrash.getLogger().e(Util.TAG, AnrHandler fileObserver onEvent failed, e);}}};try {// 启动FileObserver 监控fileObserver.startWatching();} catch (Exception e) {fileObserver null;XCrash.getLogger().e(Util.TAG, AnrHandler fileObserver startWatching failed, e);} }private void handleAnr(String filepath) {...// 读取anr文件 /data/anr/trace*.txt。返回文件内容String trace getTrace(filepath, anrTime.getTime());//删除其他的anr异常日志文件if (!FileManager.getInstance().maintainAnr()) {return;}//获取 tombstone 的文件头String emergency null;try {emergency getEmergency(anrTime, trace);} catch (Exception e) {XCrash.getLogger().e(Util.TAG, AnrHandler getEmergency failed, e);}// 创建anr异常日志保存文件File logFile null;try {String logPath String.format(Locale.US, %s/%s_%020d_%s__%s%s, logDir, Util.logPrefix, anrTime.getTime() * 1000, appVersion, processName, Util.anrLogSuffix);logFile FileManager.getInstance().createLogFile(logPath);} catch (Exception e) {XCrash.getLogger().e(Util.TAG, AnrHandler createLogFile failed, e);}if (logFile ! null){// 根据配置将日志文件头traceslogcat日志保存在文件中。} }// 高版本通过AMS获取日志 public class ANRMoniter implements Runnable {private final String TAG ANRMoniter;private HandlerThread handlerThread new HandlerThread(WatchMainHandler);private ILog logImpl;private Application app;private Handler watchHandler;private Handler mainHandler;private ScheduleCheckTask scheduleCheckTask;private int CHECK_INTERVAL 5_000;public ANRMoniter(Application app, ILog logImpl) {this.app app;this.logImpl logImpl;init();}private void init() {handlerThread.start();Looper looper handlerThread.getLooper();watchHandler new Handler(looper);mainHandler new Handler(Looper.getMainLooper());scheduleCheckTask new ScheduleCheckTask();}public void start() {watchHandler.post(this);}Overridepublic void run() {mainHandler.post(scheduleCheckTask);long endTime System.currentTimeMillis() CHECK_INTERVAL;long sleepTime endTime - System.currentTimeMillis();while (sleepTime 0) {try {Thread.sleep(sleepTime);} catch (InterruptedException e) {e.printStackTrace();}sleepTime endTime - System.currentTimeMillis();}if (scheduleCheckTask.isBlocking()) {logImpl.Loge(TAG,main handler blocking);checkRealANR(mainHandler.getLooper().getThread().getStackTrace());}scheduleCheckTask.reset();watchHandler.post(this);}private void checkRealANR(StackTraceElement[] stack) {ThreadPool.getInstance().execute(new Runnable() {Overridepublic void run() {ActivityManager.ProcessErrorStateInfo processErrorStateInfo getANRInfo(app);if (processErrorStateInfo ! null) {logImpl.Loge(TAG,ANR action);//real ANRRuntimeException e new RuntimeException(processErrorStateInfo.shortMsg);e.setStackTrace(stack);e.printStackTrace();logImpl.Loge(TAG,e.getMessage());}}});}private ActivityManager.ProcessErrorStateInfo getANRInfo(Application app) {try {final long sleepTime 500L;final long loop 20;long times 0;do {ActivityManager activityManager (ActivityManager) app.getSystemService(Context.ACTIVITY_SERVICE);ListActivityManager.ProcessErrorStateInfo processesInErrorState activityManager.getProcessesInErrorState();if (processesInErrorState ! null) {for (ActivityManager.ProcessErrorStateInfo proc : processesInErrorState) {if (proc.condition ActivityManager.ProcessErrorStateInfo.NOT_RESPONDING) {return proc;}}}Thread.sleep(sleepTime);} while (times loop);} catch (Exception e) {e.printStackTrace();}return null;}private class ScheduleCheckTask implements Runnable {private boolean isBlocking;ScheduleCheckTask() {isBlocking true;}Overridepublic void run() {isBlocking false;}public boolean isBlocking() {return isBlocking;}public void reset() {isBlocking true;}} } 自定义线程WatchDog参考 package com.aispeech.util;import android.os.Handler; import android.os.HandlerThread; import android.os.Looper; import android.os.Message; import android.util.Log;import com.aispeech.common.ThreadNameUtil; import com.aispeech.lite.BaseKernel;import java.util.Vector; import java.util.concurrent.ConcurrentHashMap; import java.util.concurrent.atomic.AtomicInteger;/** * Description: 检测Kernel层 是否阻塞的工具类 * Author: junlong.huang * CreateTime: 2023/8/21 */ public class KernelWatchDog {private static final String TAG KernelWatchDog;HandlerThread innerThread;Handler innerHandler;long timeoutMillis 2000;static final int MSG_INCREMENT 0x01;private static volatile KernelWatchDog mInstance;private ConcurrentHashMapBaseKernel, AtomicInteger monitorMap;private VectorBaseKernel removeList;public static KernelWatchDog getInstance() {if (mInstance null) {synchronized (KernelWatchDog.class) {if (mInstance null) {mInstance new KernelWatchDog();}}}return mInstance;}private KernelWatchDog() {init();}private void init() {monitorMap new ConcurrentHashMap();removeList new Vector();innerThread new HandlerThread(ThreadNameUtil.getSimpleThreadName(watchdog-k));innerThread.start();innerHandler new InnerHandler(innerThread.getLooper());innerHandler.sendMessage(innerHandler.obtainMessage(MSG_INCREMENT));}public void addChecker(BaseKernel baseKernel) {Log.i(TAG, addChecker: baseKernel.getInnerThreadName());monitorMap.put(baseKernel, new AtomicInteger(baseKernel.getTick()));}public void removeChecker(BaseKernel baseKernel) {if (monitorMap.containsKey(baseKernel)) {Log.i(TAG, removeChecker: baseKernel.getInnerThreadName());monitorMap.remove(baseKernel);}}class InnerHandler extends Handler {public InnerHandler(Looper looper) {super(looper);}Overridepublic void handleMessage(Message msg) {super.handleMessage(msg);if (innerHandler null) return;switch (msg.what) {case MSG_INCREMENT:if (monitorMap null || monitorMap.size() 0) {innerHandler.sendMessageDelayed(innerHandler.obtainMessage(MSG_INCREMENT), timeoutMillis);break;}for (BaseKernel baseKernel : monitorMap.keySet()) {if (baseKernel.getInnerThread() ! null !baseKernel.getInnerThread().isAlive()) {Log.i(TAG, Detected thread quit,Add to list to be removed);removeList.add(baseKernel);continue;}AtomicInteger lastTick monitorMap.get(baseKernel);if (lastTick null) lastTick new AtomicInteger(baseKernel.getTick());if (lastTick.get() ! baseKernel.getTick()) {Log.w(TAG, Detected target thread may blocked,export thread stack);Thread innerThread baseKernel.getInnerThread();if (innerThread ! null) {Log.w(TAG, getThreadStack(innerThread.getStackTrace()));}}lastTick.incrementAndGet();baseKernel.tick();}for (BaseKernel baseKernel : removeList) {monitorMap.remove(baseKernel);}removeList.clear();innerHandler.sendMessageDelayed(innerHandler.obtainMessage(MSG_INCREMENT), timeoutMillis);break;}}}public void release() {innerHandler.removeMessages(MSG_INCREMENT);innerThread.quit();monitorMap.clear();removeList.clear();}private String getThreadStack(StackTraceElement[] elements) {StringBuilder stackTraceString new StringBuilder();for (StackTraceElement element : elements) {stackTraceString.append(element.toString()).append(\n);}return stackTraceString.toString();}}卡顿检测 matrix 字节码插桩慢函数检测采样率法通过一个外置的工作线程Handler按一段时间采样如果大部分都是某个方法则这个方法可能存在风险点 /** * 按照一定频率采样 * 目标是找到卡顿时刻前后的堆栈做大致定位无法做到精准定位 * 原则上采样越高定位越精准 * 还有目前只采样了java层的堆栈c层的需要另外实现这个后续补充 */ public class CallstackSampler {private static final String TAG CallstackSampler;private final Thread thread;private final Handler mHandler;private final long sThreshold 1000;private final Runnable mRunnable new Runnable() {Overridepublic void run() {doSample();mHandler.postDelayed(this, sThreshold);}};public CallstackSampler(Thread thread) {this.thread thread;HandlerThread mWorkThread new HandlerThread(StackSampler thread.getName());mWorkThread.start();mHandler new Handler(mWorkThread.getLooper());}private void doSample() {// 采集指定线程当前堆栈信息StackTraceElement[] stackTrace thread.getStackTrace();String stackTraceString Arrays.toString(stackTrace);if (!stackTraceString.contains(nativePollOnce)) {Log.d(TAG, thread.getName() Callstack sample taken at time: System.currentTimeMillis() stackTraceString);}}public void startSampling() {mHandler.postDelayed(mRunnable, sThreshold);}public void stopSampling() {mHandler.removeCallbacks(mRunnable);} }主线程耗时检测设置一个printer CPU 优化案例 线程池复用减少CPU调度开销资源拷贝优化减少读取IO时间线程命名方便定位问题非必要内容延迟初始化初始化任务优先级分配削峰填谷
http://www.w-s-a.com/news/232347/

相关文章:

  • 网站建设济南云畅网络广州电力建设有限公司网站
  • 查看公司信息的网站思特奇是外包公司吗
  • 制作企业网站的目的啥都能看的浏览器
  • 做网站可以用哪些语言如何进行网站运营与规划
  • 做效果图网站有哪些电子商城网站制作数据库
  • 小刘网站建设wordpress调用php文件上传
  • 建设银行对账网站网络营销广告案例
  • 做网站开票是多少个点的票wordpress扫码提交数据库
  • 织梦网站改版需要怎么做企业网站备案管理系统
  • 大规模网站开发语言宁夏建设职业技术学院网站
  • 寻花问柳专注做一家男人爱的网站北京展台设计制作
  • 中卫网站设计做自己的卡盟网站
  • 广州网站推广自助做网站人家直接百度能搜到的
  • 电子商务网站建设目标及利益分析安徽建设厅网站施
  • 制作网站策划书网站建设公司的性质
  • 哪个网站可以做免费宣传简单的网页设计网站
  • 福州专业网站制作公司金湖建设局网站
  • 好的移动端网站模板下载兰州线上广告推广
  • 宁波高端建站深圳品牌营销策划机构
  • 权威网站优化价格建设厅科技中心网站首页
  • 保定模板建站软件腾讯云做淘客网站
  • 单位建设一个网站的费用正规刷手机单做任务网站
  • 北京定制网站价格开网店怎么卖到外国
  • 做网站 后端是谁来做的工程建设指挥部网站
  • wordpress建站 云打印昆明 网站设计
  • 太原网站建设设计网站建设策划书(建设前的市场分析)
  • 哪里有制作网站电商新手入门知识
  • 制作网站的后台文昌网站建设 myvodo
  • 网站 购买移动网站制作
  • 南京网站网站建设学校英山做网站多少钱