p50, p95, and p99 Latency: Calculation and Examples
Calculate latency percentiles from a small dataset, reproduce the results in JavaScript, and understand what averages and tail latency reveal.
A latency percentile gives the duration at or below which a proportion of measured requests completed. p50 describes the middle; p95 and p99 describe the slower tail. Report sample size, time window, failures, and calculation method.
Illustrative dataset
These 20 sorted durations are made-up teaching data in milliseconds, not a benchmark:
100, 100, 100, 100, 100, 100, 100, 100, 100, 100,
100, 100, 100, 100, 100, 100, 100, 100, 500, 2000Eighteen requests took 100 ms, one took 500 ms, and one took 2,000 ms. Their sum is 4,300 ms. The average is 4,300 / 20 = 215 ms. That average alone does not reveal the two-second request.
Calculate percentiles using nearest rank
Sort N values, calculate rank = ceil(p × N), and take the value at that one-based rank. Here p is 0.50, 0.95, or 0.99.
| Metric | Calculation | Result |
|---|---|---|
| Mean | 4,300 / 20 | 215 ms |
| p50 | ceil(0.50 × 20) = rank 10 | 100 ms |
| p95 | ceil(0.95 × 20) = rank 19 | 500 ms |
| p99 | ceil(0.99 × 20) = rank 20 | 2,000 ms |
Ties mean more than 50% can be at or below p50. Do not assume exactly 5% are slower than p95. Nearest-rank p50 can also differ from a median definition that averages the two middle observations.
Reproduce it in JavaScript
Save as percentiles.mjs and run node percentiles.mjs.
const samples = [...Array(18).fill(100), 500, 2000];
function nearestRank(values, p) {
if (!values.length || p <= 0 || p > 1) throw new Error('Invalid sample or p');
const sorted = [...values].sort((a, b) => a - b);
return sorted[Math.ceil(p * sorted.length) - 1];
}
console.log({
mean: samples.reduce((sum, n) => sum + n, 0) / samples.length,
p50: nearestRank(samples, 0.50),
p95: nearestRank(samples, 0.95),
p99: nearestRank(samples, 0.99),
});Expected output: mean 215, p50 100, p95 500, p99 2000.
Why dashboards may disagree
Some tools interpolate between values; others estimate quantiles from histograms. With 20 observations, nearest-rank p99 is just the maximum. This arithmetic example is too small to characterize a stable production tail.
Check the tool's calculation method and whether its timer includes DNS, connections, transfer, and retries. This article does not assert that API Test Lab's backend uses nearest rank.
Use averages and percentiles together
Averages summarize total time; percentiles reveal variation. Compare them with throughput and failures for the same route, window, region, and workload. A high-volume fast route can hide a slow business-critical route in aggregate data.
Do not average daily p95 values to derive monthly p95. Merge compatible samples or histograms. Report timeouts separately rather than silently excluding them.
Apply this to a load test
Verify correctness, then run a controlled workload. Compare sample counts, percentiles, throughput, and errors before and after one change. Use the bottleneck workflow to connect tail latency to server measurements.
Inspect requests in API Test Lab, then check load allowances on pricing. A low p95 matters only when responses are correct and failures remain acceptable.