跳表

作者: xyt001 | 来源:发表于2019-12-11 23:24 被阅读0次
package skiplist

import (
    "math"
    "math/rand"
)

type (
    SkipList struct {
        head      *element
        cacheList []*element
        maxLevel  int
    }

    element struct {
        next []*element
        key  int
        val  interface{}
    }
)

func NewSkipList(maxLevel int) *SkipList {
    return &SkipList{
        head: &element{
            next: make([]*element, maxLevel),
            key:  math.MinInt32,
            val:  nil,
        },
        cacheList: make([]*element, maxLevel),
        maxLevel:  maxLevel,
    }
}

func (sl *SkipList) Set(key int, val interface{}) {
    var (
        next *element
        prev = sl.head
    )

    for i := sl.maxLevel - 1; i >= 0; i-- {
        next = prev.next[i]
        for next != nil && next.key < key {
            prev = next
            next = next.next[i]
        }
        sl.cacheList[i] = prev
    }

    if elm := sl.cacheList[0].next[0]; elm != nil && elm.key == key {
        sl.cacheList[0].val = val
        return
    }

    insertData := &element{
        next: make([]*element, sl.randomLevel()),
        key:  key,
        val:  val,
    }

    for i := 0; i < len(insertData.next); i++ {
        insertData.next[i] = sl.cacheList[i].next[i]
        sl.cacheList[i].next[i] = insertData
    }
}

func (sl *SkipList) Get(key int) (interface{}, bool) {
    var (
        prev = sl.head
        next *element
    )

    for i := sl.maxLevel - 1; i >= 0; i-- {
        next = prev.next[i]
        for next != nil && next.key < key {
            prev = next
            next = next.next[i]
        }
    }

    if next != nil && next.key == key {
        return next.val, true
    }

    return nil, false
}

func (sl *SkipList) Del(key int) (interface{}, bool) {
    var (
        prev = sl.head
        next *element
    )

    for i := sl.maxLevel - 1; i >= 0; i-- {
        next = prev.next[i]
        for next != nil && next.key < key {
            prev = next
            next = next.next[i]
        }
        sl.cacheList[i] = prev
    }

    if elm := sl.cacheList[0].next[0]; elm == nil || elm.key != key {
        return nil, false
    }

    val := sl.cacheList[0].val

    for i := 0; i < len(sl.cacheList[0].next[0].next); i++ {
        sl.cacheList[i].next[i] = sl.cacheList[i].next[i].next[i]
    }

    return val, true
}

func (sl *SkipList) randomLevel() int {
    level := 1

    for {
        if rand.Intn(1) == 0 {
            level++
        } else {
            return level
        }

        if level >= sl.maxLevel {
            return sl.maxLevel
        }
    }
}


相关文章

  • 跳表

    跳表的定义 跳表(SkipList):增加了向前指针的链表叫做跳表。跳表全称叫做跳跃表,简称跳表。跳表是一个随机化...

  • 跳表

    跳表的定义 跳表(SkipList):增加了向前指针的链表叫做跳表。跳表全称叫做跳跃表,简称跳表。跳表是一个随机化...

  • HBase内存管理之MemStore

    基于跳表实现的MemStore基础模型 实现MemStore模型的数据结构是SkipList(跳表),跳表可以实现...

  • 2.跳表的基本实现和特性

    一、跳表 跳表的设计与实现为啥 redis 使用跳表(skiplist)而不是使用 red-black redis...

  • 有关跳跃表的干货都在这里

    跳表的数据结构 跳表全称叫做跳跃表,简称跳表。跳表是一个随机化的数据结构,实质就是一种可以进行二分查找的有序链表。...

  • [AlgoGo]跳表SkipList

    跳表是什么 跳表的实现基于链表,弥补了链表不便于查找的缺点,所以跳表其实不是表(table)而是链(list)。跳...

  • 知识快速回顾(数据结构+算法)

    打卡时间:2020-2-23 19:46 ~ 20:30 跳表 什么是跳表 ? 跳表是一种高效的链表结构,它通过增...

  • 跳表skiplist

    增加了向前指针的链表叫作跳表。跳表全称叫做跳跃表,简称跳表。跳表是一个随机化的数据结构,实质就是一种可以进行二分查...

  • 03、数组、链表、跳表

    数组 链表 跳表 ![ 跳表在工程中的应用LRU Cache - Linked listhttps://www.j...

  • 【算法打卡60天】Day15跳表:为什么Redis一定要用跳表来

    Day15学习内容主要为以下三点:1.如何理解“跳表”?跳表:链表加多级索引的结构。跳表使用空间换时间的设计思路,...

网友评论

      本文标题:跳表

      本文链接:https://www.haomeiwen.com/subject/stqzgctx.html