You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

484 lines
11 KiB

3 years ago
3 years ago
  1. package skiplist
  2. // adapted from https://github.com/MauriceGit/skiplist/blob/master/skiplist.go
  3. import (
  4. "bytes"
  5. "fmt"
  6. "math/bits"
  7. "math/rand"
  8. "time"
  9. )
  10. const (
  11. // maxLevel denotes the maximum height of the skiplist. This height will keep the skiplist
  12. // efficient for up to 34m entries. If there is a need for much more, please adjust this constant accordingly.
  13. maxLevel = 25
  14. )
  15. type SkipList struct {
  16. startLevels [maxLevel]*SkipListElementReference
  17. endLevels [maxLevel]*SkipListElementReference
  18. maxNewLevel int
  19. maxLevel int
  20. // elementCount int
  21. }
  22. // NewSeedEps returns a new empty, initialized Skiplist.
  23. // Given a seed, a deterministic height/list behaviour can be achieved.
  24. // Eps is used to compare keys given by the ExtractKey() function on equality.
  25. func NewSeed(seed int64) *SkipList {
  26. // Initialize random number generator.
  27. rand.Seed(seed)
  28. //fmt.Printf("SkipList seed: %v\n", seed)
  29. list := &SkipList{
  30. maxNewLevel: maxLevel,
  31. maxLevel: 0,
  32. // elementCount: 0,
  33. }
  34. return list
  35. }
  36. // New returns a new empty, initialized Skiplist.
  37. func New() *SkipList {
  38. return NewSeed(time.Now().UTC().UnixNano())
  39. }
  40. // IsEmpty checks, if the skiplist is empty.
  41. func (t *SkipList) IsEmpty() bool {
  42. return t.startLevels[0] == nil
  43. }
  44. func (t *SkipList) generateLevel(maxLevel int) int {
  45. level := maxLevel - 1
  46. // First we apply some mask which makes sure that we don't get a level
  47. // above our desired level. Then we find the first set bit.
  48. var x = rand.Uint64() & ((1 << uint(maxLevel-1)) - 1)
  49. zeroes := bits.TrailingZeros64(x)
  50. if zeroes <= maxLevel {
  51. level = zeroes
  52. }
  53. return level
  54. }
  55. func (t *SkipList) findEntryIndex(key []byte, level int) int {
  56. // Find good entry point so we don't accidentally skip half the list.
  57. for i := t.maxLevel; i >= 0; i-- {
  58. if t.startLevels[i] != nil && bytes.Compare(t.startLevels[i].Key, key) < 0 || i <= level {
  59. return i
  60. }
  61. }
  62. return 0
  63. }
  64. func (t *SkipList) findExtended(key []byte, findGreaterOrEqual bool) (foundElem *SkipListElement, ok bool) {
  65. foundElem = nil
  66. ok = false
  67. if t.IsEmpty() {
  68. return
  69. }
  70. index := t.findEntryIndex(key, 0)
  71. var currentNode *SkipListElement
  72. currentNode = t.startLevels[index].Load()
  73. // In case, that our first element is already greater-or-equal!
  74. if findGreaterOrEqual && compareElement(currentNode, key) > 0 {
  75. foundElem = currentNode
  76. ok = true
  77. return
  78. }
  79. for {
  80. if compareElement(currentNode, key) == 0 {
  81. foundElem = currentNode
  82. ok = true
  83. return
  84. }
  85. // Which direction are we continuing next time?
  86. if currentNode.Next[index] != nil && bytes.Compare(currentNode.Next[index].Key, key) <= 0 {
  87. // Go right
  88. currentNode = currentNode.Next[index].Load()
  89. } else {
  90. if index > 0 {
  91. // Early exit
  92. if currentNode.Next[0] != nil && bytes.Compare(currentNode.Next[0].Key, key) == 0 {
  93. currentNodeNext := currentNode.Next[0].Load()
  94. foundElem = currentNodeNext
  95. ok = true
  96. return
  97. }
  98. // Go down
  99. index--
  100. } else {
  101. // Element is not found and we reached the bottom.
  102. if findGreaterOrEqual {
  103. foundElem = currentNode.Next[index].Load()
  104. ok = foundElem != nil
  105. }
  106. return
  107. }
  108. }
  109. }
  110. }
  111. // Find tries to find an element in the skiplist based on the key from the given ListElement.
  112. // elem can be used, if ok is true.
  113. // Find runs in approx. O(log(n))
  114. func (t *SkipList) Find(key []byte) (elem *SkipListElement, ok bool) {
  115. if t == nil || key == nil {
  116. return
  117. }
  118. elem, ok = t.findExtended(key, false)
  119. return
  120. }
  121. // FindGreaterOrEqual finds the first element, that is greater or equal to the given ListElement e.
  122. // The comparison is done on the keys (So on ExtractKey()).
  123. // FindGreaterOrEqual runs in approx. O(log(n))
  124. func (t *SkipList) FindGreaterOrEqual(key []byte) (elem *SkipListElement, ok bool) {
  125. if t == nil || key == nil {
  126. return
  127. }
  128. elem, ok = t.findExtended(key, true)
  129. return
  130. }
  131. // Delete removes an element equal to e from the skiplist, if there is one.
  132. // If there are multiple entries with the same value, Delete will remove one of them
  133. // (Which one will change based on the actual skiplist layout)
  134. // Delete runs in approx. O(log(n))
  135. func (t *SkipList) Delete(key []byte) {
  136. if t == nil || t.IsEmpty() || key == nil {
  137. return
  138. }
  139. index := t.findEntryIndex(key, t.maxLevel)
  140. var currentNode *SkipListElement
  141. var nextNode *SkipListElement
  142. for {
  143. if currentNode == nil {
  144. nextNode = t.startLevels[index].Load()
  145. } else {
  146. nextNode = currentNode.Next[index].Load()
  147. }
  148. // Found and remove!
  149. if nextNode != nil && compareElement(nextNode, key) == 0 {
  150. if currentNode != nil {
  151. currentNode.Next[index] = nextNode.Next[index]
  152. currentNode.Save()
  153. }
  154. if index == 0 {
  155. if nextNode.Next[index] != nil {
  156. nextNextNode := nextNode.Next[index].Load()
  157. nextNextNode.Prev = currentNode.Reference()
  158. nextNextNode.Save()
  159. }
  160. // t.elementCount--
  161. nextNode.DeleteSelf()
  162. }
  163. // Link from start needs readjustments.
  164. startNextKey := t.startLevels[index].Key
  165. if compareElement(nextNode, startNextKey) == 0 {
  166. t.startLevels[index] = nextNode.Next[index]
  167. // This was our currently highest node!
  168. if t.startLevels[index] == nil {
  169. t.maxLevel = index - 1
  170. }
  171. }
  172. // Link from end needs readjustments.
  173. if nextNode.Next[index] == nil {
  174. t.endLevels[index] = currentNode.Reference()
  175. }
  176. nextNode.Next[index] = nil
  177. }
  178. if nextNode != nil && compareElement(nextNode, key) < 0 {
  179. // Go right
  180. currentNode = nextNode
  181. } else {
  182. // Go down
  183. index--
  184. if index < 0 {
  185. break
  186. }
  187. }
  188. }
  189. }
  190. // Insert inserts the given ListElement into the skiplist.
  191. // Insert runs in approx. O(log(n))
  192. func (t *SkipList) Insert(key, value []byte) {
  193. if t == nil || key == nil {
  194. return
  195. }
  196. level := t.generateLevel(t.maxNewLevel)
  197. // Only grow the height of the skiplist by one at a time!
  198. if level > t.maxLevel {
  199. level = t.maxLevel + 1
  200. t.maxLevel = level
  201. }
  202. elem := &SkipListElement{
  203. Id: rand.Int63(),
  204. Next: make([]*SkipListElementReference, t.maxNewLevel, t.maxNewLevel),
  205. Level: int32(level),
  206. Key: key,
  207. Value: value,
  208. }
  209. // t.elementCount++
  210. newFirst := true
  211. newLast := true
  212. if !t.IsEmpty() {
  213. newFirst = compareElement(elem, t.startLevels[0].Key) < 0
  214. newLast = compareElement(elem, t.endLevels[0].Key) > 0
  215. }
  216. normallyInserted := false
  217. if !newFirst && !newLast {
  218. normallyInserted = true
  219. index := t.findEntryIndex(key, level)
  220. var currentNode *SkipListElement
  221. var nextNodeRef *SkipListElementReference
  222. for {
  223. if currentNode == nil {
  224. nextNodeRef = t.startLevels[index]
  225. } else {
  226. nextNodeRef = currentNode.Next[index]
  227. }
  228. var nextNode *SkipListElement
  229. // Connect node to next
  230. if index <= level && (nextNodeRef == nil || bytes.Compare(nextNodeRef.Key, key) > 0) {
  231. elem.Next[index] = nextNodeRef
  232. if currentNode != nil {
  233. currentNode.Next[index] = elem.Reference()
  234. currentNode.Save()
  235. }
  236. if index == 0 {
  237. elem.Prev = currentNode.Reference()
  238. if nextNodeRef != nil {
  239. nextNode = nextNodeRef.Load()
  240. nextNode.Prev = elem.Reference()
  241. nextNode.Save()
  242. }
  243. }
  244. }
  245. if nextNodeRef != nil && bytes.Compare(nextNodeRef.Key, key) <= 0 {
  246. // Go right
  247. if nextNode == nil {
  248. // reuse nextNode when index == 0
  249. nextNode = nextNodeRef.Load()
  250. }
  251. currentNode = nextNode
  252. } else {
  253. // Go down
  254. index--
  255. if index < 0 {
  256. break
  257. }
  258. }
  259. }
  260. }
  261. // Where we have a left-most position that needs to be referenced!
  262. for i := level; i >= 0; i-- {
  263. didSomething := false
  264. if newFirst || normallyInserted {
  265. if t.startLevels[i] == nil || bytes.Compare(t.startLevels[i].Key, key) > 0 {
  266. if i == 0 && t.startLevels[i] != nil {
  267. startLevelElement := t.startLevels[i].Load()
  268. startLevelElement.Prev = elem.Reference()
  269. startLevelElement.Save()
  270. }
  271. elem.Next[i] = t.startLevels[i]
  272. t.startLevels[i] = elem.Reference()
  273. }
  274. // link the endLevels to this element!
  275. if elem.Next[i] == nil {
  276. t.endLevels[i] = elem.Reference()
  277. }
  278. didSomething = true
  279. }
  280. if newLast {
  281. // Places the element after the very last element on this level!
  282. // This is very important, so we are not linking the very first element (newFirst AND newLast) to itself!
  283. if !newFirst {
  284. if t.endLevels[i] != nil {
  285. endLevelElement := t.endLevels[i].Load()
  286. endLevelElement.Next[i] = elem.Reference()
  287. endLevelElement.Save()
  288. }
  289. if i == 0 {
  290. elem.Prev = t.endLevels[i]
  291. }
  292. t.endLevels[i] = elem.Reference()
  293. }
  294. // Link the startLevels to this element!
  295. if t.startLevels[i] == nil || bytes.Compare(t.startLevels[i].Key, key) > 0 {
  296. t.startLevels[i] = elem.Reference()
  297. }
  298. didSomething = true
  299. }
  300. if !didSomething {
  301. break
  302. }
  303. }
  304. elem.Save()
  305. }
  306. // GetSmallestNode returns the very first/smallest node in the skiplist.
  307. // GetSmallestNode runs in O(1)
  308. func (t *SkipList) GetSmallestNode() *SkipListElement {
  309. return t.startLevels[0].Load()
  310. }
  311. // GetLargestNode returns the very last/largest node in the skiplist.
  312. // GetLargestNode runs in O(1)
  313. func (t *SkipList) GetLargestNode() *SkipListElement {
  314. return t.endLevels[0].Load()
  315. }
  316. // Next returns the next element based on the given node.
  317. // Next will loop around to the first node, if you call it on the last!
  318. func (t *SkipList) Next(e *SkipListElement) *SkipListElement {
  319. if e.Next[0] == nil {
  320. return t.startLevels[0].Load()
  321. }
  322. return e.Next[0].Load()
  323. }
  324. // Prev returns the previous element based on the given node.
  325. // Prev will loop around to the last node, if you call it on the first!
  326. func (t *SkipList) Prev(e *SkipListElement) *SkipListElement {
  327. if e.Prev == nil {
  328. return t.endLevels[0].Load()
  329. }
  330. return e.Prev.Load()
  331. }
  332. // ChangeValue can be used to change the actual value of a node in the skiplist
  333. // without the need of Deleting and reinserting the node again.
  334. // Be advised, that ChangeValue only works, if the actual key from ExtractKey() will stay the same!
  335. // ok is an indicator, wether the value is actually changed.
  336. func (t *SkipList) ChangeValue(e *SkipListElement, newValue []byte) (ok bool) {
  337. // The key needs to stay correct, so this is very important!
  338. e.Value = newValue
  339. e.Save()
  340. return true
  341. }
  342. // String returns a string format of the skiplist. Useful to get a graphical overview and/or debugging.
  343. func (t *SkipList) println() {
  344. print("start --> ")
  345. for i, l := range t.startLevels {
  346. if l == nil {
  347. break
  348. }
  349. if i > 0 {
  350. print(" -> ")
  351. }
  352. next := "---"
  353. if l != nil {
  354. next = string(l.Key)
  355. }
  356. print(fmt.Sprintf("[%v]", next))
  357. }
  358. println()
  359. nodeRef := t.startLevels[0]
  360. for nodeRef != nil {
  361. print(fmt.Sprintf("%v: ", string(nodeRef.Key)))
  362. node := nodeRef.Load()
  363. for i := 0; i <= int(node.Level); i++ {
  364. l := node.Next[i]
  365. next := "---"
  366. if l != nil {
  367. next = string(l.Key)
  368. }
  369. if i == 0 {
  370. prev := "---"
  371. if node.Prev != nil {
  372. prev = string(node.Prev.Key)
  373. }
  374. print(fmt.Sprintf("[%v|%v]", prev, next))
  375. } else {
  376. print(fmt.Sprintf("[%v]", next))
  377. }
  378. if i < int(node.Level) {
  379. print(" -> ")
  380. }
  381. }
  382. println()
  383. nodeRef = node.Next[0]
  384. }
  385. print("end --> ")
  386. for i, l := range t.endLevels {
  387. if l == nil {
  388. break
  389. }
  390. if i > 0 {
  391. print(" -> ")
  392. }
  393. next := "---"
  394. if l != nil {
  395. next = string(l.Key)
  396. }
  397. print(fmt.Sprintf("[%v]", next))
  398. }
  399. println()
  400. }