p99

package module
v0.2.0 Latest Latest
Warning

This package is not in the latest version of its module.

Go to latest
Published: Aug 20, 2026 License: BSD-3-Clause Imports: 6 Imported by: 0

README

p99.Go

Low-cost generation of performance percentiles (p50, p90, p99, p99.9, etc.).

Language License GitHub release Last Commit Go Go Reference

Table of Contents

Introduction

p99 is a lightweight, low-overhead library designed for generating real-time performance percentiles in high-frequency or latency-sensitive environments.

p99.Go is the Go implementation.

How It Works

Histogram is a low-overhead, zero-allocation, fixed-size structure designed to track event durations (typically in nanoseconds) using 64 logarithmic buckets.

  • Logarithmic Bucketing: The bucket boundaries are spaced as powers of two:
    • Bucket 0 represents [0, 1] nanoseconds;
    • Bucket 1 represents [2, 3] nanoseconds;
    • Bucket 2 represents [4, 7] nanoseconds;
    • Bucket i represents [2^i, 2^(i+1) - 1] nanoseconds.
  • Branchless Indexing: Finding the correct bucket index for an incoming duration is extremely fast. It is computed in a few CPU instructions using bits.Len64.
  • Linear Interpolation: Percentile queries iterate through the buckets to find the target rank and perform linear interpolation within the matching bucket to approximate the exact percentile duration.

Performance & Trade-offs

Performance Claims
  • Zero Allocation: Histogram does not allocate memory on the heap during creation, event insertion, or percentile queries under normal operation. It is a compact structure that can reside entirely on the stack or be embedded in other structures.
  • Ultra-Low Latency Insertion: Recording a latency measurement (PushEventTimeNs) is designed for minimal overhead.
  • Fast Queries: Querying percentiles (such as ValueAtP99()) is designed to terminate early when events cluster in lower-indexed buckets.
Trade-offs & Sacrifices
  • Logarithmic Precision: To achieve zero allocation and constant-time operations, Histogram sacrifices exact precision. It does not store individual event times.
  • Approximation: Percentile values are approximated using linear interpolation within the bucket boundaries. For very large values, the bucket width is wider, which leads to a wider approximation range.

Installation

Install:

go get "github.com/synesissoftware/p99.Go"

Use:

import "github.com/synesissoftware/p99.Go"

Components

Constants
Name Value Description
BucketCount 64 Number of logarithmic buckets in a Histogram
VersionMajor 0 Major version number
VersionMinor 2 Minor version number
VersionPatch 0 Patch version number
VersionAB ver2go.Release (0xFFFF) Final-release αβ-designator
Functions
Function Description
New() Returns a zero-initialized histogram
Version() Returns the packed 64-bit library version
VersionString() Returns the string form of the library version
BucketIndex(timeInNs uint64) int Calculates the bucket index for a duration
BucketRange(index int) (bool, uint64, uint64) Returns the inclusive nanosecond range for a bucket
Structures
Histogram

A low-cost, zero-allocation, 64-bucket logarithmic histogram designed for recording event durations in nanoseconds and querying high-resolution percentiles.

Minimal Example
package main

import (
	"fmt"
	"time"

	"github.com/synesissoftware/p99.Go"
)

func main() {
	h := p99.New()

	h.PushEventTimeNs(150)
	h.PushEventTimeUs(5)
	h.PushEventTimeMs(10)
	h.PushEventDuration(250 * time.Nanosecond)

	fmt.Println("events:", h.EventCount())

	if ok, p99val := h.ValueAtP99(); ok {
		fmt.Printf("p99: %d ns\n", p99val)
	}
}

Examples

Examples are provided in the examples directory, along with a markdown description for each. A detailed list of them is provided in EXAMPLES.md.

Project Information

Where to get help

GitHub Page

Contribution guidelines

Defect reports, feature requests, and pull requests are welcome on https://github.com/synesissoftware/p99.Go.

Dependencies
Development Dependencies
License

p99.Go is released under the 3-clause BSD license. See LICENSE for details.

Documentation

Overview

Package p99 provides a low-cost, zero-allocation histogram for recording event durations in nanoseconds and querying performance percentiles (p50, p90, p99, p99.9, and so on).

Histogram uses 64 logarithmic power-of-two buckets and performs linear interpolation within buckets to approximate percentile values. It is designed for high-frequency latency measurement with minimal overhead.

Index

Constants

View Source
const (
	VersionMajor uint16 = 0
	VersionMinor uint16 = 2
	VersionPatch uint16 = 0
	VersionAB    uint16 = ver2go.Release
)
View Source
const BucketCount = 64

Specifies the number of logarithmic buckets in a Histogram.

Variables

This section is empty.

Functions

func BucketIndex

func BucketIndex(timeInNs uint64) int

Calculates the bucket index for a duration in nanoseconds.

func BucketRange

func BucketRange(index int) (bool, uint64, uint64)

Attempts to obtain the inclusive nanosecond range for the given bucket index.

func Version

func Version() uint64

Version returns this library's version as a packed 64-bit integer, formed by ver2go.CombineVersion from VersionMajor, VersionMinor, VersionPatch, and VersionAB. The result is suitable for numeric comparison: a later release has a strictly greater value than an earlier one that uses the same packing.

func VersionString

func VersionString() string

VersionString returns this library's version as a human-readable string, formed by ver2go.CalcVersionString from VersionMajor, VersionMinor, VersionPatch, and VersionAB. For a final (non-prerelease) version the result is of the form "MAJOR.MINOR.PATCH", e.g. "0.2.0".

Types

type Histogram

type Histogram struct {
	// contains filtered or unexported fields
}

A low-cost, zero-allocation, fixed-size structure for recording event durations in nanoseconds and querying high-resolution percentiles.

func New

func New() *Histogram

Returns a zero-initialized histogram.

func (*Histogram) BucketValue

func (h *Histogram) BucketValue(index int) (bool, uint64)

Attempts to obtain the count of events in the bucket at index.

func (*Histogram) Buckets

func (h *Histogram) Buckets() [BucketCount]uint64

Returns a copy of all bucket counts.

func (*Histogram) Clear

func (h *Histogram) Clear()

Resets the histogram to the equivalent of a newly constructed instance.

func (*Histogram) EventCount

func (h *Histogram) EventCount() uint64

Returns the number of recorded events.

func (*Histogram) EventTimeTotal

func (h *Histogram) EventTimeTotal() (bool, uint64)

Attempts to obtain the total event time in nanoseconds when no overflow has occurred.

func (*Histogram) EventTimeTotalRaw

func (h *Histogram) EventTimeTotalRaw() uint64

Returns the total event time in nanoseconds regardless of whether overflow has occurred.

func (*Histogram) GoString

func (h *Histogram) GoString() string

A verbose debug representation of the histogram.

func (*Histogram) HasOverflowed

func (h *Histogram) HasOverflowed() bool

Reports whether an overflow has occurred.

func (*Histogram) MaxEventTime

func (h *Histogram) MaxEventTime() (bool, uint64)

Attempts to obtain the maximum event time observed.

func (*Histogram) MinEventTime

func (h *Histogram) MinEventTime() (bool, uint64)

Attempts to obtain the minimum event time observed.

func (*Histogram) PushEventDuration

func (h *Histogram) PushEventDuration(d time.Duration) bool

Records an event with the given duration. The nanosecond value is truncated to uint64.

func (*Histogram) PushEventTimeMs

func (h *Histogram) PushEventTimeMs(timeInMs uint64) bool

Records an event with the given number of milliseconds.

func (*Histogram) PushEventTimeNs

func (h *Histogram) PushEventTimeNs(timeInNs uint64) bool

Records an event with the given number of nanoseconds. Returns false if overflow has occurred or the running total would overflow.

func (*Histogram) PushEventTimeS

func (h *Histogram) PushEventTimeS(timeInS uint64) bool

Records an event with the given number of seconds.

func (*Histogram) PushEventTimeUs

func (h *Histogram) PushEventTimeUs(timeInUs uint64) bool

Records an event with the given number of microseconds.

func (*Histogram) String

func (h *Histogram) String() string

A compact debug representation of the histogram.

func (*Histogram) ValueAtP50

func (h *Histogram) ValueAtP50() (bool, uint64)

Attempts to obtain the approximated duration at p50 (50th percentile).

func (*Histogram) ValueAtP75

func (h *Histogram) ValueAtP75() (bool, uint64)

Attempts to obtain the approximated duration at p75 (75th percentile).

func (*Histogram) ValueAtP90

func (h *Histogram) ValueAtP90() (bool, uint64)

Attempts to obtain the approximated duration at p90 (90th percentile).

func (*Histogram) ValueAtP95

func (h *Histogram) ValueAtP95() (bool, uint64)

Attempts to obtain the approximated duration at p95 (95th percentile).

func (*Histogram) ValueAtP99

func (h *Histogram) ValueAtP99() (bool, uint64)

Attempts to obtain the approximated duration at p99 (99th percentile).

func (*Histogram) ValueAtP99_5

func (h *Histogram) ValueAtP99_5() (bool, uint64)

Attempts to obtain the approximated duration at p99.5 (99.5th percentile).

func (*Histogram) ValueAtP99_9

func (h *Histogram) ValueAtP99_9() (bool, uint64)

Attempts to obtain the approximated duration at p99.9 (99.9th percentile).

func (*Histogram) ValueAtP99_99

func (h *Histogram) ValueAtP99_99() (bool, uint64)

Attempts to obtain the approximated duration at p99.99 (99.99th percentile).

func (*Histogram) ValueAtP99_999

func (h *Histogram) ValueAtP99_999() (bool, uint64)

Attempts to obtain the approximated duration at p99.999 (99.999th percentile).

func (*Histogram) ValueAtP99_999_9

func (h *Histogram) ValueAtP99_999_9() (bool, uint64)

Attempts to obtain the approximated duration at p99.9999 (99.9999th percentile).

func (*Histogram) ValueAtPercentile

func (h *Histogram) ValueAtPercentile(percentile float64) (bool, uint64)

Attempts to obtain the approximated duration in nanoseconds at the given percentile. Percentile is clamped to [0, 100].

Directories

Path Synopsis
examples
build_histogram command
Demonstrates recording event durations and querying percentiles.
Demonstrates recording event durations and querying percentiles.
libver command
version command

Jump to

Keyboard shortcuts

? : This menu
/ : Search site
f or F : Jump to
y or Y : Canonical URL