性能优化是什么
提升软件系统处理能力,减少不必要的消耗,充分发掘计算机算力。
为什么要做性能优化
- 带来用户体验的提升
- 降低成本,提高效率
性能优化的层面
- 业务层优化:针对特定场景,具体问题,具体分析,容易获得较大性能提升
- 语言运行时的优化:解决通用的性能问题(内存分配),考虑更多场景,做权衡,对全公司都有收益,Tradeoffs。
- 数据驱动:自动化性能分析工具-pprof,依靠数据,首先优化最大瓶颈(较明显性能收益)
性能优化和软件质量
- 软件质量至关重要
- 在保证接口稳定的前提下改进具体实现
- 测试用例:覆盖尽可能多的场景,方便回归
- 文档:做了什么,没做什么,有什么效果
- 隔离:控制是否开启优化
- 可观测:必要的日志输出
自动内存管理
- 动态内存:malloc()
- 避免手动管理:double free,use after free
- 三个任务:
- 为新对象分配空间
- 找到存活对象
- 回收死亡对象的内存空间
相关概念
- mutator :业务线程,分配新对象,修改对象指向关系
- Collector :GC线程,找到存活对象,回收死亡对象的空间
- Serial GC : 只有一个collector
- Parallel GC :支持多个collector同时回收的GC算法
- Concurrent GC:mutator和collector可同时执行,collector必须感知对象指向关系的变化
- 评价GC算法:
- 安全性:不能回收存活的对象
- 吞吐率:1-GC时间/总时间
- 暂停时间
- 内存开销
- 追踪垃圾回收(tracing garbage collection)
- 引用计数(reference counting)
追踪垃圾回收
- 对象被回收的条件:不可达
- 标记根对象
- 标记可达对象
- 清理不可达对象
- Copying GC:存活对象复制到别处
- Mark-sweep GC:死亡对象标记可分配
- Mark-compact GC:移动,整理存活对象
- 根据对象生命周期,使用不同的标记和清理策略
分代GC
- 分代假说:most objects die youngC
- intuition:很对对象分配出来后很快就不再使用
- 对象年龄:经历过GC的次数
- 对年轻和年老的对象指定不同的GC策略
- 不同年龄对象处于heap不同区域
- 年轻代:常规对象分配,由于存活对象少,可用copying collection,GC吞吐率高
- 老年代:对象趋于存活,反复复制开销大,使用mark-sweep collection
引用计数
- 每个对象都有与之相关的引用数目
- 对象存活条件:引用数大于0
- 优点:内存管理的操作被平摊到程序执行过程中,不需要了解runtime的实现细节
- 缺点:维护开销大,无法回收环形数据结构,回收内存时依然可能引发暂停。
总结
自动内存管理是一种用于管理计算机程序中内存分配和回收的技术。它可以帮助程序员避免手动管理内存分配和回收的复杂性,从而减少程序中出现内存泄漏和其他内存相关问题的可能性。自动内存管理通常通过垃圾回收技术来实现。垃圾回收器会定期扫描程序中的内存,找出不再使用的内存块并将其回收,以便在需要时重新分配给程序。除了垃圾回收之外,自动内存管理还可以通过其他技术来实现,例如引用计数。引用计数是一种跟踪对象引用次数的技术。当一个对象的引用次数降为零时,它就不再被使用,可以被回收。对空间上的内存管理势必会导致时间上的劣势,如何平衡两者就是我们需要研究的地方了。