BenchmarkMode可以指定不同的测试指标
根据指定的指标不同, 测试出来的报表会有很大区别
下面介绍一下4种不同的Benchmark测试指标
1. @BenchmarkMode(Mode.Throughput)
吞吐量测试 ```java @Warmup(iterations = 1, time = 1, timeUnit = TimeUnit.SECONDS)//预热次数和时间 @Measurement(iterations = 1, time = 1, timeUnit = TimeUnit.SECONDS)//测试次数和时间 public class Sample2_BenchmarkMode {
@Benchmark @BenchmarkMode(Mode.Throughput) //吞吐量测试, 输出报告: 每单位时间该方法会执行多少次 @OutputTimeUnit(TimeUnit.DAYS) //输出报告的时间单位 public void measureThroughput() throws InterruptedException {
TimeUnit.MILLISECONDS.sleep(100);
}
public static void main(String[] args) throws RunnerException {
Options opt = new OptionsBuilder()
.include(Sample2_BenchmarkMode.class.getSimpleName())
.forks(1)
.build();
new Runner(opt).run();
} }
输出结果:
Benchmark Mode Cnt Score Error Units Sample2_BenchmarkMode.measureThroughput thrpt 789482.124 ops/day
结果: `789482.124 ops/day` 方法一天可以执行 789482.124 次
---
<a name="Brq6g"></a>
# 2. @BenchmarkMode(Mode.AverageTime)
方法平均耗时测试
```java
@Warmup(iterations = 1, time = 1, timeUnit = TimeUnit.SECONDS)//预热次数和时间
@Measurement(iterations = 1, time = 1, timeUnit = TimeUnit.SECONDS)//测试次数和时间
public class Sample2_BenchmarkMode {
@Benchmark
@BenchmarkMode(Mode.AverageTime) //平均耗时测试, 输出报告: 每次操作耗时
@OutputTimeUnit(TimeUnit.SECONDS) //耗时的单位
public void measureAvgTime() throws InterruptedException {
TimeUnit.MILLISECONDS.sleep(100);
}
public static void main(String[] args) throws RunnerException {
Options opt = new OptionsBuilder()
.include(Sample2_BenchmarkMode.class.getSimpleName())
.forks(1)
.build();
new Runner(opt).run();
}
}
输出结果:
Benchmark Mode Cnt Score Error Units
Sample2_BenchmarkMode.measureAvgTime avgt 0.109 s/op
结果: 0.109 s/op
平均每次操作耗时 0.109秒
3. @BenchmarkMode(Mode.SampleTime)
抽样测试 ```java @Warmup(iterations = 1, time = 1, timeUnit = TimeUnit.SECONDS)//预热次数和时间 @Measurement(iterations = 1, time = 1, timeUnit = TimeUnit.SECONDS)//测试次数和时间 public class Sample2_BenchmarkMode {
@Benchmark @BenchmarkMode(Mode.SampleTime) //抽样测试, 输出报告: 会在执行过程中采样(每次操作耗时), 最快的, 50%快的, 90%, 95%, 99%, 99.9%, 99.99%, 100% @OutputTimeUnit(TimeUnit.SECONDS) public void measureSamples() throws InterruptedException {
TimeUnit.MILLISECONDS.sleep(100);
}
public static void main(String[] args) throws RunnerException {
Options opt = new OptionsBuilder()
.include(Sample2_BenchmarkMode.class.getSimpleName())
.forks(1)
.build();
new Runner(opt).run();
}
}
输出结果:
Benchmark Mode Cnt Score Error Units Sample2_BenchmarkMode.measureSamples sample 10 0.109 ± 0.003 s/op Sample2_BenchmarkMode.measureSamples:measureSamples·p0.00 sample 0.107 s/op Sample2_BenchmarkMode.measureSamples:measureSamples·p0.50 sample 0.109 s/op Sample2_BenchmarkMode.measureSamples:measureSamples·p0.90 sample 0.113 s/op Sample2_BenchmarkMode.measureSamples:measureSamples·p0.95 sample 0.113 s/op Sample2_BenchmarkMode.measureSamples:measureSamples·p0.99 sample 0.113 s/op Sample2_BenchmarkMode.measureSamples:measureSamples·p0.999 sample 0.113 s/op Sample2_BenchmarkMode.measureSamples:measureSamples·p0.9999 sample 0.113 s/op Sample2_BenchmarkMode.measureSamples:measureSamples·p1.00 sample 0.113 s/op
根据置信区间展示 单次操作的耗时平均值
---
<a name="aFfhR"></a>
# 4. @BenchmarkMode(Mode.SingleShotTime)
- 单次执行测试
```java
@Warmup(iterations = 1)//预热轮数
@Measurement(iterations = 1)//测试轮数
public class Sample2_BenchmarkMode {
@Benchmark
@BenchmarkMode(Mode.SingleShotTime) //冷启动测试, 设置了这个, 此方法在一轮中只会运行一次, 这个模式主要是为了测试冷启动的性能
@OutputTimeUnit(TimeUnit.SECONDS) //输出单位秒
public void measureSingleShot() throws InterruptedException {
TimeUnit.MILLISECONDS.sleep(100);
}
public static void main(String[] args) throws RunnerException {
Options opt = new OptionsBuilder()
.include(Sample2_BenchmarkMode.class.getSimpleName())
.forks(1)
.build();
new Runner(opt).run();
}
}
输出结果:
Benchmark Mode Cnt Score Error Units
Sample2_BenchmarkMode.measureSingleShot ss 0.100 s/op
结果: 0.100 s/op
单次的操作耗时; 这个方法实际只被执行了一次
总结
以上这四种模式都是为了衡量 方法级别的代码的 性能
- Mode.Throughput : 吞吐量测试; 每一次都会被统计到, 绝大多数性能测试都是使用这种, 关注的是吞吐量
- Mode.AverageTime : 这种在运行时与吞吐量测试本质上是类似的, 只不过观察测试结果的视角不同, 更注重平均耗时
- Mode.SampleTime : 执行过程中进行随机抽样统计, 更关注执行效率是否稳定, 对性能毛刺更敏感
- Mode.SingleShotTime : 这种就是单纯为了关注冷启动的执行效率而使用的