set

package module
v0.0.0-...-7fc3201 Latest Latest
Warning

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

Go to latest
Published: Oct 4, 2024 License: MIT Imports: 4 Imported by: 0

README

Set

An implementation of a generic Set data structure in Go with an Iter function to simulate Rust's iterators and has Go's version of iterator functions, leveraging the best of both worlds.

Example

package main

import (
    "fmt"
    "log"

    "github.com/Jamlie/set"
)

type Person struct {
	Id   int
	Name string
	Age  int
}

func main() {
	intsSet := set.New[int]()
	intsSet.Insert(1)
	intsSet.Insert(2)
	intsSet.Insert(3)
	intsSet.Delete(1)

	fmt.Println(intsSet.Len())
	fmt.Println(intsSet)
	if intsSet.Contains(2) {
		fmt.Println("Set contains number 2")
	}

	uniquePeople := set.New[Person]()
	uniquePeople.Insert(Person{Id: 21, Name: "John", Age: 30})
	uniquePeople.Insert(Person{Id: 22, Name: "Jane", Age: 31})
	uniquePeople.Insert(Person{Id: 23, Name: "Roland", Age: 32})

	newUnique := uniquePeople.Clone()

	if !newUnique.Empty() {
		newUnique.Clear()
	}

	uniquePeople = uniquePeople.
		Iter().
		Map(func(k Person) Person {
			return Person{
				Id:   k.Id * 3,
				Name: k.Name,
				Age:  k.Age,
			}
		}).
		Filter(func(k Person) bool {
			return k.Id%2 == 1
		}).
		Collect()

	for k := range uniquePeople.All() {
		log.Println(k)
	}

	fmt.Println(uniquePeople)

	newPeople := set.New[Person]()

	newPeople.Collect(uniquePeople.All())

	log.Println(newPeople)
}

Documentation

Overview

Package set provides a generic implementation of a set.

A Set is a collection of unique elements, implemented using Go's built-in map type. The Set is parameterized with a type T, which must be comparable.

This package offers several functions and methods to manipulate and work with sets, including the ability to iterate over the elements, map and filter them, and collect them back into a new Set. (It's been influened by Rust)

Index

Constants

This section is empty.

Variables

This section is empty.

Functions

This section is empty.

Types

type Set

type Set[T comparable] struct {
	// contains filtered or unexported fields
}

A `Set` is implemented as a `map[T]struct{}`.

As with maps, a Set requires T to be a comparable, meaning it can accept structs if and only if they don't have a type like a slice/map/anything that is not comparable

Examples:

package main

import (
	"fmt"

	"github.com/Jamlie/set"
)

type Person struct {
	Id   int
	Name string
	Age  int
}

func main() {
	intsSet := set.New[int]()
	intsSet.Insert(1)
	intsSet.Insert(2)
	intsSet.Insert(3)
	intsSet.Delete(1)

	fmt.Println(intsSet.Len())
	fmt.Println(intsSet)
	if intsSet.Contains(2) {
		fmt.Println("Set contains number 2")
	}

	uniquePeople := set.New[Person]()
	uniquePeople.Insert(Person{Id: 21, Name: "John", Age:30})
	uniquePeople.Insert(Person{Id: 22, Name: "Jane", Age:30})
	uniquePeople.Insert(Person{Id: 23, Name: "Roland", Age:30})

	newUnique := uniquePeople.Clone()

	if !newUnique.Empty() {
		newUnique.Clear()
	}

	uniquePeople.
		Iter().
		Map(func(k Person) Person {
			return Person{
				Id:   k.Id * 3,
				Name: k.Name,
				Age:  k.Age,
			}
		}).
		Filter(func(k Person) bool {
			return k.Id%2 == 1
		}).
		Collect()
	fmt.Println(uniquePeople)
}

func FromMap

func FromMap[Map ~map[K]V, K comparable, V any](v Map) *Set[K]

Converts a map into a set

Examples:

package main

import (
	"fmt"

	"github.com/Jamlie/set"
)

func main() {
	m := map[string]int{
		"first":  1,
		"second": 2,
		"last":   3,
	}

	v := set.FromMap(m)

	fmt.Println(v)
}

func FromSlice

func FromSlice[Slice ~[]T, T comparable](v Slice) *Set[T]

Converts a slice into a set

Examples:

package main

import (
	"fmt"

	"github.com/Jamlie/set"
)

func main() {
	arr := []string{"first", "second", "last"}

	v := set.FromSlice(arr)

	fmt.Println(v)
}

func New

func New[T comparable]() *Set[T]

Create a new instance of Set with Go's default capacity.

Examples:

package main

import "github.com/Jamlie/set"

func main() {
	v := set.New[int]()
	_ = v
}

func WithCapacity

func WithCapacity[T comparable](capacity int) *Set[T]

Create a new instance of Set with a specified capacity

The set will be able to hold at least `capacity` without reallocating until it's full. This function will panic if capacity is negative.

Examples:

package main

import "github.com/Jamlie/set"

func main() {
	v := set.WithCapacity[int](10)
	_ = v
}

func (*Set[T]) All

func (s *Set[T]) All() iter.Seq[T]

A way to iterate through Set using a range-loop

Examples:

package main

import (
	"log"

	"github.com/Jamlie/set"
)

func main() {
	v := set.New[int]()
	v.Insert(3)
	v.Insert(2)
	v.Insert(1)

	for k := range v.All() {
		log.Println(k)
	}
}

func (*Set[T]) Clear

func (s *Set[T]) Clear()

Clears the set, removing all values.

Examples:

package main

import (
	"github.com/Jamlie/assert"
	"github.com/Jamlie/set"
)

func main() {
	v := set.New[string]()
	v.Insert("first")
	v.Insert("second")
	v.Insert("third")
	v.Clear()
	assert.Assert(v.Len() == 0, "Should have all elements removed")
}

func (*Set[T]) Clone

func (s *Set[T]) Clone() *Set[T]

Returns a clone of the set.

Examples:

package main

import (
	"github.com/Jamlie/assert"
	"github.com/Jamlie/set"
)

func main() {
	v := set.New[int]()
	v.Insert(1)
	v.Insert(2)
	v.Insert(4)
	clone := v.Clone()
	assert.Assert(clone.Len() == 3, "Should have the same elements and the same length")
}

func (*Set[T]) Collect

func (s *Set[T]) Collect(seq iter.Seq[T])

Collect allows passing any `iter.Seq[T]` and replaces all values in the existing set. Note: Collect changes the whole set.

Examples:

package main

import (
	"log"

	"github.com/Jamlie/set"
)

func main() {
	v := set.New[int]()
	v.Insert(3)
	v.Insert(2)
	v.Insert(1)

	newSet := set.New[int]()
	newSet.Insert(5)
	newSet.Collect(v.All())
	log.Println(newSet) // [3 1 2]
}

func (*Set[T]) Contains

func (s *Set[T]) Contains(k T) bool

Returns `true` if the set contains a value.

Examples:

package main

import (
	"github.com/Jamlie/assert"
	"github.com/Jamlie/set"
)

func main() {
	v := set.New[int]()
	v.Insert(1)
	v.Insert(2)
	v.Insert(4)
	assert.Assert(v.Contains(3) == false, "Number doesn't exist")
	assert.Assert(v.Contains(4) == true, "Number exist")
}

func (*Set[T]) Delete

func (s *Set[T]) Delete(k T)

Removes a value from the set.

Removeing a value that does not exists will result in nothing.

Examples:

package main

import (
	"github.com/Jamlie/assert"
	"github.com/Jamlie/set"
)

func main() {
	v := set.New[int]()
	v.Insert(1)
	v.Insert(2)
	v.Delete(1)
	v.Delete(3)
	assert.Assert(v.Len() == 1, "Delete should remove at the value if exists")
}

func (*Set[T]) Empty

func (s *Set[T]) Empty() bool

Returns `true` if the set contains no elements.

Examples:

package main

import (
	"github.com/Jamlie/assert"
	"github.com/Jamlie/set"
)

func main() {
	v := set.New[int]()
	assert.Assert(v.Empty(), "Empty set");
	v.Add(1);
	assert.Assert(!v.is_empty(), "Set should be empty");
}

func (*Set[T]) Insert

func (s *Set[T]) Insert(k T)

Adds a value to the set.

Inserting the same value more than once won't change the set

Examples:

package main

import (
	"github.com/Jamlie/assert"
	"github.com/Jamlie/set"
)

func main() {
	v := set.New[int]()
	v.Insert(1)
	v.Insert(1)
	assert.Assert(v.Len() == 1, "Should not insert the same value more than once")
}

func (*Set[T]) InsertSeq

func (s *Set[T]) InsertSeq(seq iter.Seq[T])

InsertSeq allows entering any `iter.Seq[T]` and appends all values into the existing set.

Examples:

package main

import (
	"log"

	"github.com/Jamlie/set"
)

func main() {
	v := set.New[int]()
	v.Insert(3)
	v.Insert(2)
	v.Insert(1)

	newSet := set.New[int]()
	newSet.Insert(4)
	newSet.InsertSeq(v.All())
	log.Println(newSet) // [2 3 1 4]
}

func (*Set[T]) Iter

func (s *Set[T]) Iter() *setIter[T]

An iterator visiting all elements in arbitrary order.

Examples:

package main

import "github.com/Jamlie/set"

func main() {
	v := set.New[string]()
	v.Insert("first")
	v.Insert("second")
	v.Insert("third")

	v = v.Iter().Map(...).Filter(...).Collect()
}

func (*Set[T]) Keys

func (s *Set[T]) Keys() []T

Returns a slice containing the keys of the set in an arbitrary ordered.

Examples:

package main

import (
	"github.com/Jamlie/assert"
	"github.com/Jamlie/set"
)

func main() {
	v := set.New[int]()
	v.Insert(1)
	v.Insert(2)
	v.Insert(4)
	keys := v.Keys()
	assert.Assert(len(keys) == 3, "Should have the same elements and the same length")
	assert.Assert(sameSlice(keys, []int{2,1,4}), "Should have the same elements and the same length")
}

// check https://stackoverflow.com/questions/36000487/check-for-equality-on-slices-without-order for source code
func sameSlice[T comparable](x, y []T) bool

func (*Set[T]) Len

func (s *Set[T]) Len() int

The number of elements the set currently has.

Examples:

package main

import (
	"github.com/Jamlie/assert"
	"github.com/Jamlie/set"
)

func main() {
	v := set.New[int]()
	v.Insert(1)
	v.Insert(2)
	v.Insert(3)
	assert.Assert(v.Len() == 3, "Gets the number of elements")
}

func (Set[T]) String

func (s Set[T]) String() string

Returns a stringified version of the set with elements in an arbitrary order

Examples:

package main

import (
	"fmt"

	"github.com/Jamlie/set"
)

func main() {
	v := set.New[int]()
	v.Insert(1)
	v.Insert(2)
	v.Insert(3)
	fmt.Println(v)
}

Directories

Path Synopsis
Package concurrentset provides a generic implementation of a thread-safe concurrent set.
Package concurrentset provides a generic implementation of a thread-safe concurrent set.
Package orderedset provides a generic implementation of an ordered set.
Package orderedset provides a generic implementation of an ordered set.

Jump to

Keyboard shortcuts

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