skiplist

package module
v0.0.0-...-d63941a Latest Latest
Warning

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

Go to latest
Published: Jan 3, 2023 License: MIT Imports: 6 Imported by: 0

README

Skip List in Golang

Go Go Doc Go Report Coverage Status

This package was created by forking the skiplist library that Huandu's great job

Skip list is an ordered map. See wikipedia page skip list to learn algorithm details about this data structure.

Highlights in this implementation:

  • Based on generic No reflection, No interface{}
  • Support custom comparable function so that any type can be used as key.
  • Rand source and max level can be changed per list. It can be useful in performance critical scenarios.
  • Optional memory pool use
  • Optional thread-safe instance SafeSkipList, SkipList

Warrning

Not fully tested

Install

Install this package through go get.

go get github.com/ironpark/skiplist

Example

Basic Usage

Here is a quick sample.

package main

import (
    "fmt"
    "github.com/ironpark/skiplist"
)

func main() {
    // Create a skip list with int key.
    list := skiplist.New[int,any](skiplist.NumberComparator[int])

    // Add some values. Value can be anything.
    list.Set(12, "hello world")
    list.Set(34, 56)
    list.Set(78, 90.12)

    // Get element by index.
    elem := list.Get(34)                // Value is stored in elem.Value.
    fmt.Println(elem.Value)             // Output: 56
    next := elem.Next()                 // Get next element.
    prev := next.Prev()                 // Get previous element.
    fmt.Println(next.Value, prev.Value) // Output: 90.12    56

    // Or, directly get value just like a map
    val, ok := list.GetValue(34)
    fmt.Println(val, ok) // Output: 56  true

    // Find first elements with score greater or equal to key
    foundElem := list.Find(30)
    fmt.Println(foundElem.Key(), foundElem.Value) // Output: 34 56

    // Remove an element for key.
    list.Remove(34)
}
Thread Safe
package main

import (
  "fmt"
  "github.com/ironpark/skiplist"
  "sync"
)

func main() {
  // Create a skip list with int key.
  list := skiplist.New[int, struct{}](skiplist.NumberComparator[int],skiplist.WithMutex())
  wg := sync.WaitGroup{}
  wg.Add(100)
  for i := 0; i < 100; i++ {
    go func(i int) {
      list.Set(i, struct{}{})
      wg.Done()
    }(i)
  }
  wg.Wait()
  fmt.Println(list.Keys())
}

License

This library is licensed under MIT license. See LICENSE for details.

Documentation

Overview

Package skiplist implement skip list data structure. See wikipedia for more details about this data structure. http://en.wikipedia.org/wiki/Skip_list

Skip list is basically an ordered map.

Here is a sample to use this package.

// Creates a new skip list and restricts key type to int-like types.
list := skiplist.New(skiplist.Int)

// Adds some values for keys.
list.Set(20, "Hello")
list.Set(10, "World")
list.Set(40, true) // Value type is not restricted.
list.Set(40, 1000) // Replace the of an existing element.

// Finds elements.
e := list.Get(10)           // Returns the element with the key.
_ = e.Value.(string)
v, ok := list.GetValue(20)  // Directly get value of the element. If the key is not found, ok is false.
v2 := list.MustGetValue(10) // Directly get value of the element. Panic if the key is not found.
notFound := list.Get(15)    // Returns nil if the key is not found.

// Removes an element and gets removed element.
old := list.Remove(40)
notFound := list.Remove(-20) // Returns nil if the key is not found.

// Initializes the list again to clean up all elements in the list.
list.Init()

Copyright 2022 Iron Park. All rights reserved.

Index

Constants

View Source
const (
	DefaultMaxLevel            = 18
	DefaultProbability float64 = 1 / math.E
)

DefaultMaxLevel is the default level for all newly created skip lists. It can be changed globally. Changing it will not affect existing lists. And all skip lists can update max level after creation through `SetMaxLevel()` method.

Variables

This section is empty.

Functions

func BytesComparator

func BytesComparator[K Bytes](lk, rk K) int

func NumberComparator

func NumberComparator[K Numbers](lk, rk K) int

Types

type Bytes

type Bytes interface {
	~[]byte | ~string
}

type Comparable

type Comparable[K any] func(lhs, rhs K) int

Comparable defines a comparable func.

func Reverse

func Reverse[K any](comparable Comparable[K]) Comparable[K]

Reverse creates a reversed comparable.

type Element

type Element[K, V any] struct {
	Value V
	// contains filtered or unexported fields
}

Element is an element node of a skip list.

func (*Element[K, V]) Index

func (elem *Element[K, V]) Index() int

func (*Element[K, V]) Key

func (elem *Element[K, V]) Key() K

Key returns the key of the elem.

func (*Element[K, V]) Level

func (elem *Element[K, V]) Level() int

Level returns the level of this elem.

func (*Element[K, V]) Next

func (elem *Element[K, V]) Next() *Element[K, V]

Next returns next adjacent elem.

func (*Element[K, V]) NextLevel

func (elem *Element[K, V]) NextLevel(level int) *Element[K, V]

NextLevel returns next element at specific level. If level is invalid, returns nil.

func (*Element[K, V]) Prev

func (elem *Element[K, V]) Prev() *Element[K, V]

Prev returns previous adjacent elem.

type Numbers

type Numbers interface {
	constraints.Integer | constraints.Float | rune
}

type Option

type Option func(option *Options)

Option is a function used to set Options

func WithMaxLevel

func WithMaxLevel(maxLevel int) Option

WithMaxLevel sets max level of Skiplist

func WithMutex

func WithMutex() Option

WithMutex sets Skiplist goroutine-safety

func WithPool

func WithPool() Option

WithPool sets probability of Skiplist

func WithProbability

func WithProbability(probability float64) Option

WithProbability sets probability of Skiplist

type Options

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

Options holds Skiplist's options

type SkipList

type SkipList[K, V any] interface {
	Init() SkipList[K, V]
	SetProbability(newProbability float64)
	Front() (front *Element[K, V])
	Back() *Element[K, V]
	Len() int
	Set(key K, value V) (element *Element[K, V])
	FindNext(start *Element[K, V], key K) (next *Element[K, V])
	Find(key K) (elem *Element[K, V])
	Get(key K) (elem *Element[K, V])
	GetValue(key K) (val V, ok bool)
	MustGetValue(key K) V
	Remove(key K) (elem *Element[K, V])
	RemoveFront() (front *Element[K, V])
	RemoveBack() (back *Element[K, V])
	RemoveElement(elem *Element[K, V])
	MaxLevel() int
	Values() (values []V)
	Index(elem *Element[K, V]) (i int)
	Keys() (keys []K)
	SetMaxLevel(level int) (old int)
}

func New

func New[K, V any](comparable Comparable[K], options ...Option) (skipList SkipList[K, V])

New creates a new skip list with comparable to compare keys.

There are lots of pre-defined strict-typed keys like Int, Float64, String, etc. We can create custom comparable by implementing Comparable interface.

Jump to

Keyboard shortcuts

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