Started implementing structures for gox.

This commit is contained in:
Andrey Parhomenko 2023-04-28 16:14:03 +03:00
parent eddf2c345c
commit 302da3ec07
4 changed files with 199 additions and 0 deletions

View file

@ -3,6 +3,7 @@ package main
import (
"github.com/surdeus/godat/src/mapx"
"github.com/surdeus/godat/src/slicex"
"github.com/surdeus/godat/src/llx"
"fmt"
)
@ -39,4 +40,13 @@ func main() {
fmt.Printf("%q\n", mapx.Values(m))
fmt.Printf("%q\n", mapx.Reverse(m))
fmt.Printf("%v\n", mapx.Reverse(m1))
ll := llx.New[int]()
ll.Append(0)
ll.Append(1)
ll.Append(2)
ll.Set(1, 256)
for p := range ll.Range() {
fmt.Println(p)
}
}

129
src/llx/main.go Normal file
View file

@ -0,0 +1,129 @@
package llx
// Linked list X .
// The package implements better variation of
// linked list than in standard library since it uses
// the new conception of generics.
type LinkedList[V any] struct {
// First empty element (not used to store values).
// For fast pushing.
before *Element[V]
// Points to the last for fast appending.
last *Element[V]
// Length.
ln int
}
type Element[V any] struct {
prev *Element[V]
next *Element[V]
value V
}
type Pair[V any] struct {
I int
V V
}
// Returns new empty linked list storing the V type.
func New[V any]() *LinkedList[V] {
return &LinkedList[V]{
&Element[V]{},
nil,
0,
}
}
// Get length of the linked list.
func (ll *LinkedList[V]) Len() int {
return ll.ln
}
// Get the index-indexed element itself.
func (ll *LinkedList[V]) GetEl(index int) (*Element[V], bool) {
if ll.ln <= index {
return nil, false
}
p := ll.before
for i := 0 ; i <= index ; i++ {
p = p.next
}
return p, true
}
// Get the value of index-indexed element.
func (ll *LinkedList[V]) Get(index int) (V, bool) {
el, ok := ll.GetEl(index)
var v V
if ok {
v = el.value
}
return v, ok
}
// Set the new value in i-indexed element.
func (ll *LinkedList[V]) Set(i int, v V) (bool) {
el, ok := ll.GetEl(i)
if !ok {
return false
}
el.value = v
return true
}
// Push in the beginning of the list.
func (ll *LinkedList[V]) Push(v V) {
prevNext := ll.before.next
nextNext := &Element[V]{
next: prevNext,
prev: nil,
value: v,
}
ll.before.next = nextNext
ll.ln++
if ll.ln == 1 {
ll.last = ll.before.next
}
}
// Append to the end of the list.
func (ll *LinkedList[V]) Append(v V) {
if ll.ln == 0 {
ll.Push(v)
return
}
last := &Element[V]{
next: nil,
prev: ll.last,
value: v,
}
lastBuf := ll.last
lastBuf.next = last
ll.last = last
ll.ln++
}
// Returns a channel of Pair that contains index and the value.
func (ll *LinkedList[V]) Range() chan Pair[V] {
chn := make(chan Pair[V])
go func(){
i := -1
el := ll.before
for el.next != nil {
i++
el = el.next
chn <- Pair[V]{i, el.value}
}
close(chn)
}()
return chn
}

View file

@ -1,5 +1,40 @@
package mapx
// The type implements map type where
// you can get, set and delete by value
// since it store everything as ONLY entity
// both for keys and values way.
// Use only when you do not care about the order.
type UniqMap[K, V comparable] struct {
store map[K] V
rstore map[V] K
}
// Returns new empty UniqMap.
func NewUniq[K, V comparable]() *UniqMap[K, V] {
return &UniqMap[K, V]{
make(map[K] V),
make(map[V] K),
}
}
// Sets new value v for the k key.
func (m *UniqMap[K, V]) Set(k K, v V) {
m.store[k] = v
m.rstore[v] = k
}
// Get value by the k key.
func (m *UniqMap[K, V]) Get(k K) (V, bool) {
v, ok := m.store[k]
return v, ok
}
func (m *UniqMap[K, V]) GetByValue(v V) (K, bool) {
k, ok := m.rstore[v]
return k, ok
}
func Keys[K comparable, V any](m map[K] V) []K {
r := make([]K, 0, len(m))
for k := range m {

25
src/poolx/main.go Normal file
View file

@ -0,0 +1,25 @@
package poolx
// The package implements ordered
// pool structure without any indexex.
// Should be used with only-one-value based
// structures.
type Pool[V comparable] struct {
store map[V] uint64
last uint64
}
// Returns new empty pool.
func New[V comparable]() *Pool {
return &Pool{
make(map[V] uint64),
0,
}
}
func (p *Pool[V]) Push(v V) {
p.last++
map[V] = p.last
}