Rebranding.
This commit is contained in:
parent
8009ad0e84
commit
75a5d77699
13 changed files with 213 additions and 116 deletions
|
@ -2,13 +2,28 @@ package main
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"fmt"
|
"fmt"
|
||||||
"github.com/mojosa-software/godat/llx"
|
"github.com/reklesio/gods/lists"
|
||||||
)
|
)
|
||||||
|
|
||||||
func main() {
|
func main() {
|
||||||
ll := llx.New[string]("zero", "one", "two", "three", "four", "five")
|
list := lists.NewSingly[string]("zero", "one", "two", "three", "four", "five")
|
||||||
ll.Push("-one", "-two")
|
fmt.Println(list)
|
||||||
|
list.Push("-one", "-two")
|
||||||
|
fmt.Println(list)
|
||||||
|
|
||||||
ll.Swap(0, 2)
|
list.Swap(0, 2)
|
||||||
fmt.Println(ll.Slice())
|
fmt.Println(list)
|
||||||
|
|
||||||
|
intList := lists.NewSingly[int](100, 5, -1, 1000, 200, 1337)
|
||||||
|
fmt.Println(intList)
|
||||||
|
|
||||||
|
intList.Sort(func(vi, vj int) bool {
|
||||||
|
return vi < vj
|
||||||
|
})
|
||||||
|
fmt.Println(intList)
|
||||||
|
|
||||||
|
intList.Sort(func(vi, vj int) bool {
|
||||||
|
return vj < vi
|
||||||
|
})
|
||||||
|
fmt.Println(intList)
|
||||||
}
|
}
|
||||||
|
|
14
container.go
Normal file
14
container.go
Normal file
|
@ -0,0 +1,14 @@
|
||||||
|
package gods
|
||||||
|
|
||||||
|
// All the containers must implement the interface.
|
||||||
|
type Container[V any] interface {
|
||||||
|
Empty() bool
|
||||||
|
Size() int
|
||||||
|
Clear()
|
||||||
|
Values() []V
|
||||||
|
//String() string
|
||||||
|
}
|
||||||
|
|
||||||
|
type Comparator[V any] interface {
|
||||||
|
Less(v1, v2 V)
|
||||||
|
}
|
10
errors.go
Normal file
10
errors.go
Normal file
|
@ -0,0 +1,10 @@
|
||||||
|
package gods
|
||||||
|
|
||||||
|
import (
|
||||||
|
"errors"
|
||||||
|
)
|
||||||
|
|
||||||
|
var (
|
||||||
|
IndexRangeErr = errors.New("index out of range")
|
||||||
|
)
|
||||||
|
|
2
go.mod
2
go.mod
|
@ -1,4 +1,4 @@
|
||||||
module github.com/mojosa-software/godat
|
module github.com/reklesio/gods
|
||||||
|
|
||||||
go 1.19
|
go 1.19
|
||||||
|
|
||||||
|
|
34
lists/main.go
Normal file
34
lists/main.go
Normal file
|
@ -0,0 +1,34 @@
|
||||||
|
package lists
|
||||||
|
|
||||||
|
import (
|
||||||
|
"github.com/reklesio/gods"
|
||||||
|
)
|
||||||
|
|
||||||
|
// The interface all the lists must implement.
|
||||||
|
type List[V any] interface {
|
||||||
|
gods.Container[V]
|
||||||
|
Push(...V)
|
||||||
|
// Get length of the list
|
||||||
|
Len() int
|
||||||
|
// Get the value by index.
|
||||||
|
Get(int) V
|
||||||
|
// Delete the value by index.
|
||||||
|
Del(int)
|
||||||
|
// Change already existing value.
|
||||||
|
Set(int, V)
|
||||||
|
// Add the values
|
||||||
|
Add(...V)
|
||||||
|
|
||||||
|
// Insert the value before the specifed index.
|
||||||
|
InsB(V, int)
|
||||||
|
// Insert the value after the specified index.
|
||||||
|
InsA(int, V)
|
||||||
|
|
||||||
|
// Swap elements by indexes specified in arguments.
|
||||||
|
Swap(i, j int)
|
||||||
|
|
||||||
|
// The sort function that gets the Less function as argument
|
||||||
|
// and sorts the list corresponding to it.
|
||||||
|
Sort(gods.LessFunc[V])
|
||||||
|
}
|
||||||
|
|
|
@ -1,111 +1,111 @@
|
||||||
package llx
|
package lists
|
||||||
|
|
||||||
|
import (
|
||||||
|
"github.com/reklesio/gods"
|
||||||
|
"sort"
|
||||||
|
"fmt"
|
||||||
|
)
|
||||||
|
|
||||||
// Linked list X .
|
// Linked list X .
|
||||||
// The package implements better variation of
|
// The package implements better variation of
|
||||||
// linked list than in standard library since it uses
|
// linked list than in standard library since it uses
|
||||||
// the new conception of generics.
|
// the new conception of generics.
|
||||||
|
|
||||||
// The type represents linked list data structure.
|
// The type represents singly linked list data structure.
|
||||||
type LinkedList[V any] struct {
|
type sLinkedList[V any] struct {
|
||||||
// First empty element (not used to store values).
|
// First empty element (not used to store values).
|
||||||
// For fast pushing.
|
// For fast pushing.
|
||||||
before *Element[V]
|
before *sElement[V]
|
||||||
// Points to the last for fast appending.
|
// Points to the last for fast appending.
|
||||||
last *Element[V]
|
last *sElement[V]
|
||||||
// Length.
|
// Length.
|
||||||
ln int
|
ln int
|
||||||
}
|
}
|
||||||
|
|
||||||
// The type represents element of the linked list.
|
// The type represents element of the linked list.
|
||||||
type Element[V any] struct {
|
type sElement[V any] struct {
|
||||||
next *Element[V]
|
next *sElement[V]
|
||||||
value V
|
value V
|
||||||
}
|
}
|
||||||
|
|
||||||
// Returns new empty linked list storing the V type.
|
func newSingly[V any](values ...V) *sLinkedList[V] {
|
||||||
func New[V any](values ...V) *LinkedList[V] {
|
ret := &sLinkedList[V]{
|
||||||
ret := &LinkedList[V]{
|
before: &sElement[V]{},
|
||||||
&Element[V]{},
|
last: nil,
|
||||||
nil,
|
ln: 0,
|
||||||
0,
|
|
||||||
}
|
}
|
||||||
|
|
||||||
ret.Append(values...)
|
ret.Add(values...)
|
||||||
return ret
|
return ret
|
||||||
}
|
}
|
||||||
|
|
||||||
// Get length of the linked list.
|
// Returns new empty linked list storing the V type.
|
||||||
func (ll *LinkedList[V]) Length() int {
|
func NewSingly[V any](values ...V) List[V] {
|
||||||
|
return newSingly[V](values...)
|
||||||
|
}
|
||||||
|
|
||||||
|
func (ll *sLinkedList[V]) Empty() bool {
|
||||||
|
return ll == nil
|
||||||
|
}
|
||||||
|
|
||||||
|
func (ll *sLinkedList[V]) Size() int {
|
||||||
return ll.ln
|
return ll.ln
|
||||||
}
|
}
|
||||||
|
|
||||||
func (ll *LinkedList[V]) Len() int {
|
func (ll *sLinkedList[V]) Clear() {
|
||||||
return ll.Length()
|
buf := newSingly[V]()
|
||||||
|
*ll = *buf
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func (ll *sLinkedList[V]) Len() int {
|
||||||
|
return ll.ln
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
// Get the index-indexed element itself.
|
// Get the index-indexed element itself.
|
||||||
func (ll *LinkedList[V]) GetEl(index int) (*Element[V], bool) {
|
func (ll *sLinkedList[V]) getEl(index int) *sElement[V] {
|
||||||
if ll.ln <= index {
|
if ll.ln <= index || index < 0 {
|
||||||
return nil, false
|
panic(gods.IndexRangeErr)
|
||||||
}
|
}
|
||||||
p := ll.before
|
p := ll.before
|
||||||
for i := 0 ; i <= index ; i++ {
|
for i := 0 ; i <= index ; i++ {
|
||||||
p = p.next
|
p = p.next
|
||||||
}
|
}
|
||||||
|
|
||||||
return p, true
|
return p
|
||||||
}
|
}
|
||||||
|
|
||||||
// Get the value of index-indexed element.
|
// Get the value of index-indexed element.
|
||||||
func (ll *LinkedList[V]) Get(index int) (V, bool) {
|
func (ll *sLinkedList[V]) Get(index int) V {
|
||||||
el, ok := ll.GetEl(index)
|
return ll.getEl(index).value
|
||||||
var v V
|
|
||||||
if ok {
|
|
||||||
v = el.value
|
|
||||||
}
|
|
||||||
|
|
||||||
return v, ok
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// Set the new value in i-indexed element.
|
// Set the new value in i-indexed element.
|
||||||
func (ll *LinkedList[V]) Set(i int, v V) (bool) {
|
func (ll *sLinkedList[V]) Set(i int, v V) {
|
||||||
el, ok := ll.GetEl(i)
|
el := ll.getEl(i)
|
||||||
if !ok {
|
|
||||||
return false
|
|
||||||
}
|
|
||||||
|
|
||||||
el.value = v
|
el.value = v
|
||||||
return true
|
|
||||||
}
|
}
|
||||||
|
|
||||||
// Insert the V value before the i-th element.
|
// Insert the V value before the i-th element.
|
||||||
func (ll *LinkedList[V]) InsertBefore(v V, i int) {
|
func (ll *sLinkedList[V]) InsB(v V, i int) {
|
||||||
if i == 0 {
|
if i == 0 {
|
||||||
ll.before = &Element[V]{
|
ll.before = &sElement[V]{
|
||||||
value: v,
|
value: v,
|
||||||
next: ll.before.next,
|
next: ll.before.next,
|
||||||
}
|
}
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
el, ok := ll.GetEl(i-1)
|
el := ll.getEl(i-1)
|
||||||
if !ok {
|
el.next = &sElement[V]{
|
||||||
panic("index out of range")
|
|
||||||
}
|
|
||||||
|
|
||||||
el.next = &Element[V]{
|
|
||||||
value: v,
|
value: v,
|
||||||
next: el.next,
|
next: el.next,
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// Insert the V value after the i-th element.
|
// Insert the V value after the i-th element.
|
||||||
func (ll *LinkedList[V]) InsertAfter(i int, v V) {
|
func (ll *sLinkedList[V]) InsA(i int, v V) {
|
||||||
el, ok := ll.GetEl(i)
|
el := ll.getEl(i)
|
||||||
if !ok {
|
el.next = &sElement[V]{
|
||||||
panic("index out of range")
|
|
||||||
}
|
|
||||||
|
|
||||||
el.next = &Element[V]{
|
|
||||||
value: v,
|
value: v,
|
||||||
next: el.next,
|
next: el.next,
|
||||||
}
|
}
|
||||||
|
@ -113,29 +113,20 @@ func (ll *LinkedList[V]) InsertAfter(i int, v V) {
|
||||||
|
|
||||||
// Swap element values indexed by i1 and i2.
|
// Swap element values indexed by i1 and i2.
|
||||||
// Panic on "index out of range".
|
// Panic on "index out of range".
|
||||||
func (ll *LinkedList[V]) Swap(i1, i2 int) {
|
func (ll *sLinkedList[V]) Swap(i1, i2 int) {
|
||||||
if i1 == i2 {
|
if i1 == i2 {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
max := ll.ln - 1
|
el1 := ll.getEl(i1)
|
||||||
if i1 < 0 || i2 < 0 || i1 > max || i2 > max {
|
el2 := ll.getEl(i2)
|
||||||
panic("index out of range")
|
|
||||||
}
|
|
||||||
|
|
||||||
el1, _ := ll.GetEl(i1)
|
|
||||||
el2, _ := ll.GetEl(i2)
|
|
||||||
|
|
||||||
el1.value, el2.value =
|
el1.value, el2.value =
|
||||||
el2.value, el1.value
|
el2.value, el1.value
|
||||||
}
|
}
|
||||||
|
|
||||||
// Deletes the element by its index.
|
// Deletes the element by its index.
|
||||||
func (ll *LinkedList[V]) Delete(i int) {
|
func (ll *sLinkedList[V]) Del(i int) {
|
||||||
if ll.ln <= i && i < 0 {
|
|
||||||
panic("index out of range")
|
|
||||||
}
|
|
||||||
|
|
||||||
if i == 0 {
|
if i == 0 {
|
||||||
ll.before.next =
|
ll.before.next =
|
||||||
ll.before.next.next
|
ll.before.next.next
|
||||||
|
@ -143,33 +134,28 @@ func (ll *LinkedList[V]) Delete(i int) {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
el1, _ := ll.GetEl(i-1)
|
el1 := ll.getEl(i-1)
|
||||||
if i == ll.ln - 1 {
|
if i == ll.ln - 1 {
|
||||||
el1.next = nil
|
el1.next = nil
|
||||||
} else {
|
} else {
|
||||||
el2, _ := ll.GetEl(i+1)
|
el2 := ll.getEl(i+1)
|
||||||
el1.next = el2
|
el1.next = el2
|
||||||
}
|
}
|
||||||
|
|
||||||
ll.ln--
|
ll.ln--
|
||||||
}
|
}
|
||||||
|
|
||||||
// Alias to Delete method.
|
|
||||||
func (ll *LinkedList[V]) Del(i int) {
|
|
||||||
ll.Delete(i)
|
|
||||||
}
|
|
||||||
|
|
||||||
// Push in the beginning of the list.
|
// Push in the beginning of the list.
|
||||||
func (ll *LinkedList[V]) Push(values ...V) {
|
func (ll *sLinkedList[V]) Push(values ...V) {
|
||||||
for _, value := range values {
|
for _, value := range values {
|
||||||
ll.push(value)
|
ll.push(value)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// Push in the beginning of the list.
|
// Push in the beginning of the list.
|
||||||
func (ll *LinkedList[V]) push(v V) {
|
func (ll *sLinkedList[V]) push(v V) {
|
||||||
prevNext := ll.before.next
|
prevNext := ll.before.next
|
||||||
nextNext := &Element[V]{
|
nextNext := &sElement[V]{
|
||||||
next: prevNext,
|
next: prevNext,
|
||||||
value: v,
|
value: v,
|
||||||
}
|
}
|
||||||
|
@ -182,19 +168,19 @@ func (ll *LinkedList[V]) push(v V) {
|
||||||
}
|
}
|
||||||
|
|
||||||
// Append to the end of the list.
|
// Append to the end of the list.
|
||||||
func (ll *LinkedList[V]) Append(values ...V) {
|
func (ll *sLinkedList[V]) Add(values ...V) {
|
||||||
for _, value := range values {
|
for _, value := range values {
|
||||||
ll.gappend(value)
|
ll.gappend(value)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
func (ll *LinkedList[V]) gappend(v V) {
|
func (ll *sLinkedList[V]) gappend(v V) {
|
||||||
if ll.ln == 0 {
|
if ll.ln == 0 {
|
||||||
ll.Push(v)
|
ll.Push(v)
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
last := &Element[V]{
|
last := &sElement[V]{
|
||||||
next: nil,
|
next: nil,
|
||||||
value: v,
|
value: v,
|
||||||
}
|
}
|
||||||
|
@ -207,28 +193,28 @@ func (ll *LinkedList[V]) gappend(v V) {
|
||||||
}
|
}
|
||||||
|
|
||||||
// Returns the first element of the linked list.
|
// Returns the first element of the linked list.
|
||||||
func (ll *LinkedList[V]) First() *Element[V] {
|
func (ll *sLinkedList[V]) First() *sElement[V] {
|
||||||
return ll.before.next
|
return ll.before.next
|
||||||
}
|
}
|
||||||
|
|
||||||
// Get elements value.
|
// Get elements value.
|
||||||
func (ll *Element[V]) Value() V {
|
func (ll *sElement[V]) Value() V {
|
||||||
return ll.value
|
return ll.value
|
||||||
}
|
}
|
||||||
|
|
||||||
// Returns the next element. If the returned value == nil,
|
// Returns the next element. If the returned value == nil,
|
||||||
// then it is the last element.
|
// then it is the last element.
|
||||||
func (ll *Element[V]) Next() *Element[V] {
|
func (ll *sElement[V]) Next() *sElement[V] {
|
||||||
return ll.next
|
return ll.next
|
||||||
}
|
}
|
||||||
|
|
||||||
// Returns the last element.
|
// Returns the last element.
|
||||||
func (ll *LinkedList[V]) Last() *Element[V] {
|
func (ll *sLinkedList[V]) Last() *sElement[V] {
|
||||||
return ll.last
|
return ll.last
|
||||||
}
|
}
|
||||||
|
|
||||||
// Returns a channel with values ordered as in list.
|
// Returns a channel with values ordered as in list.
|
||||||
func (ll *LinkedList[V]) Chan() chan V {
|
func (ll *sLinkedList[V]) Chan() chan V {
|
||||||
chn := make(chan V)
|
chn := make(chan V)
|
||||||
go func(){
|
go func(){
|
||||||
el := ll.before
|
el := ll.before
|
||||||
|
@ -242,19 +228,27 @@ func (ll *LinkedList[V]) Chan() chan V {
|
||||||
}
|
}
|
||||||
|
|
||||||
// Returns slice of values in the list ordered as in the list.
|
// Returns slice of values in the list ordered as in the list.
|
||||||
func (ll *LinkedList[V]) Slice() []V {
|
func (ll *sLinkedList[V]) Values() []V {
|
||||||
buf := make([]V, ll.Length())
|
buf := make([]V, ll.Len())
|
||||||
chn := ll.Chan()
|
|
||||||
|
|
||||||
i := 0
|
i := 0
|
||||||
for v := range chn {
|
el := ll.before
|
||||||
buf[i] = v
|
for el.next != nil {
|
||||||
|
el = el.next
|
||||||
|
buf[i] = el.value
|
||||||
i++
|
i++
|
||||||
}
|
}
|
||||||
|
|
||||||
return buf
|
return buf
|
||||||
}
|
}
|
||||||
|
|
||||||
func (ll *LinkedList[V]) Sort() {
|
func (ll *sLinkedList[V]) String() string {
|
||||||
|
return fmt.Sprintf("%v", ll.Values())
|
||||||
|
}
|
||||||
|
|
||||||
|
func (ll *sLinkedList[V]) Sort(fn gods.LessFunc[V]) {
|
||||||
|
sort.Sort(gods.CustomSort[V]{
|
||||||
|
CustomSorter: ll,
|
||||||
|
LessFunc: fn,
|
||||||
|
})
|
||||||
}
|
}
|
||||||
|
|
BIN
media/gopher.png
Normal file
BIN
media/gopher.png
Normal file
Binary file not shown.
After Width: | Height: | Size: 107 KiB |
5
mkconfig
5
mkconfig
|
@ -1,5 +0,0 @@
|
||||||
MKSHELL = sh
|
|
||||||
<$(MKINCDIR)/config
|
|
||||||
WATCH_FILES = src tmpl
|
|
||||||
CC = cc
|
|
||||||
|
|
7
mkfile
7
mkfile
|
@ -1,7 +0,0 @@
|
||||||
all: build
|
|
||||||
build:V:
|
|
||||||
go build -o ./exe/ ./cmd/...
|
|
||||||
|
|
||||||
clean:V:
|
|
||||||
rm -f ./exe/*
|
|
||||||
|
|
8
readme
8
readme
|
@ -1,8 +0,0 @@
|
||||||
# godat
|
|
||||||
|
|
||||||
Golang custom data structures for specific purposes.
|
|
||||||
|
|
||||||
- Linked list: llx
|
|
||||||
- List: listx
|
|
||||||
- Sparse array: sparsex
|
|
||||||
|
|
10
readme.md
Normal file
10
readme.md
Normal file
|
@ -0,0 +1,10 @@
|
||||||
|
# Gods
|
||||||
|
|
||||||
|
![Put a gopher image here, please](https://raw.githubusercontent.com/reklesio/gods/main/media/gopher.png)
|
||||||
|
|
||||||
|
Golang data structures.
|
||||||
|
|
||||||
|
|
||||||
|
# Tasks
|
||||||
|
|
||||||
|
- [ ] Write the tasks
|
29
sort.go
Normal file
29
sort.go
Normal file
|
@ -0,0 +1,29 @@
|
||||||
|
package gods
|
||||||
|
|
||||||
|
type Getter[V any] interface {
|
||||||
|
Get(int) V
|
||||||
|
}
|
||||||
|
|
||||||
|
type Swapper interface {
|
||||||
|
Swap(i, j int)
|
||||||
|
Len() int
|
||||||
|
}
|
||||||
|
|
||||||
|
type CustomSorter[V any] interface {
|
||||||
|
Getter[V]
|
||||||
|
Swapper
|
||||||
|
}
|
||||||
|
|
||||||
|
type LessFunc[V any] func(v1, v2 V) bool
|
||||||
|
// The type implements way to sort
|
||||||
|
// swappers via custom function.
|
||||||
|
type CustomSort[V any] struct {
|
||||||
|
CustomSorter[V]
|
||||||
|
LessFunc LessFunc[V]
|
||||||
|
}
|
||||||
|
|
||||||
|
func (cs CustomSort[V]) Less(i, j int) bool {
|
||||||
|
vi, vj := cs.Get(i), cs.Get(j)
|
||||||
|
return cs.LessFunc(vi, vj)
|
||||||
|
}
|
||||||
|
|
11
stacks/main.go
Normal file
11
stacks/main.go
Normal file
|
@ -0,0 +1,11 @@
|
||||||
|
package stacks
|
||||||
|
|
||||||
|
import (
|
||||||
|
"github.com/reklesio/gods"
|
||||||
|
)
|
||||||
|
|
||||||
|
type Stack[V any] interface {
|
||||||
|
gods.Container[V]
|
||||||
|
Push(V)
|
||||||
|
Pop() V
|
||||||
|
}
|
Loading…
Reference in a new issue