Documentation ¶
Overview ¶
Package optional implements an optional value, also sometimes called "Maybe".
The package is written in a functional style, with many top-level functions that revolve around a simple value type.
Index ¶
- func Else[T any](value Value[T], onEmpty func())
- func GetItem[T any](value Value[T]) (T, bool)
- func HasItem[T any](value Value[T]) bool
- func If[T any](value Value[T], onValue func(T))
- func IfElse[T any](value Value[T], onValue func(T), onEmpty func())
- func IsEmpty[T any](value Value[T]) bool
- func Len[T any](value Value[T]) int
- func ToSlice[T any](value Value[T]) []T
- type Value
- func Dereference[T any](t *T) Value[T]
- func FromOKResult[Item any](item Item, ok bool) Value[Item]
- func MapItem[Key comparable, Item any](m map[Key]Item, key Key) Value[Item]
- func NewEmpty[T any]() Value[T]
- func NewWithItem[T any](t T) Value[T]
- func Pointer[T any](t *T) Value[*T]
- func SliceItem[Item any](s []Item, index int) Value[Item]
Examples ¶
Constants ¶
This section is empty.
Variables ¶
This section is empty.
Functions ¶
func Else ¶ added in v1.2.0
Else calls onEmpty for values that are empty. Nothing is done if the value actually wraps an item. onEmpty may be nil.
Example ¶
package main import ( "fmt" "github.com/GodsBoss/g/optional" ) func main() { valueWithItem := optional.NewWithItem("I am an item.") emptyValue := optional.NewEmpty[string]() optional.Else( valueWithItem, func() { fmt.Println("First.") }, ) optional.Else( emptyValue, func() { fmt.Println("Second.") }, ) }
Output: Second.
func GetItem ¶
GetItem extracts the item from value if such an item exists. If not, the zero value for T is returned. The second return value signals whether a value could be extracted.
func If ¶ added in v1.2.0
If calls onValue for values wrapping an item, passing said item. Nothing is done if the value is empty. onValue may be nil.
Example ¶
package main import ( "fmt" "github.com/GodsBoss/g/optional" ) func main() { valueWithItem := optional.NewWithItem("I am an item.") emptyValue := optional.NewEmpty[string]() optional.If( valueWithItem, func(s string) { fmt.Println("First: " + s) }, ) optional.If( emptyValue, func(s string) { fmt.Println("Second: " + s) }, ) }
Output: First: I am an item.
func IfElse ¶
IfElse calls onValue for values wrapping an item, passing said item. If the value is empty, onEmpty is called instead. Both onValue and onEmpty may be nil.
Example ¶
package main import ( "fmt" "github.com/GodsBoss/g/optional" ) func main() { valueWithItem := optional.NewWithItem("I am an item.") emptyValue := optional.NewEmpty[string]() printItem := func(s string) { fmt.Println(s) } printDefault := func() { fmt.Println("I am empty.") } optional.IfElse( valueWithItem, printItem, printDefault, ) optional.IfElse( emptyValue, printItem, printDefault, ) }
Output: I am an item. I am empty.
Types ¶
type Value ¶
type Value[T any] interface { // Invoke calls f only if an item is stored with that value. Invoke(f func(item T)) }
Value represents an optional value. It may contain an item of type T.
Example (Empty) ¶
package main import ( "fmt" "github.com/GodsBoss/g/optional" ) func main() { value := optional.NewEmpty[int]() item, ok := optional.GetItem(value) fmt.Println(item) fmt.Println(ok) fmt.Println(optional.HasItem(value)) fmt.Println(optional.IsEmpty(value)) fmt.Println(optional.Len(value)) fmt.Println(len(optional.ToSlice(value))) }
Output: 0 false false true 0 0
Example (WithItem) ¶
package main import ( "fmt" "github.com/GodsBoss/g/optional" ) func main() { value := optional.NewWithItem("Hello, world!") item, ok := optional.GetItem(value) fmt.Println(item) fmt.Println(ok) fmt.Println(optional.HasItem(value)) fmt.Println(optional.IsEmpty(value)) fmt.Println(optional.Len(value)) fmt.Println(len(optional.ToSlice(value))) }
Output: Hello, world! true true false 1 1
func Dereference ¶
Dereferences converts a pointer into an optional value of the referenced type. Nil pointers become empty values, else the pointer's dereferenced value is wrapped.
Example (Nil) ¶
package main import ( "fmt" "github.com/GodsBoss/g/optional" ) func main() { var ptr *int value := optional.Dereference(ptr) fmt.Println(optional.HasItem(value)) }
Output: false
Example (Nonnil) ¶
package main import ( "fmt" "github.com/GodsBoss/g/optional" ) func main() { s := "Hello!" value := optional.Dereference(&s) if item, ok := optional.GetItem(value); ok { fmt.Println(item) } }
Output: Hello!
func FromOKResult ¶ added in v1.1.0
FromOKResult wraps the result of a function that returns an Item and a boolean to indicate whether it returned a value. Returns an empty value if ok is false, else wraps item. Does not check for zero values, so a (nil, true) return value would result in a non-empty result.
Example ¶
package main import ( "fmt" "github.com/GodsBoss/g/optional" ) func main() { // f stands in for functions that return a value and a boolean to indicate whether the // return value is meaningful, e.g. os.LookupEnv or strings.CutPrefix. f := func(s string, ok bool) (string, bool) { return s, ok } optional. FromOKResult(f("Hello, world!", true)). Invoke( func(s string) { fmt.Println(s) }, ) optional. FromOKResult(f("none", false)). Invoke( func(s string) { fmt.Println(s) }, ) }
Output: Hello, world!
func MapItem ¶
func MapItem[Key comparable, Item any](m map[Key]Item, key Key) Value[Item]
MapItem takes a map and a key, returning an empty value if that key does not exist in the map, and the corresponding item for that key otherwise. Only checks whether a map key exists and may happily wrap zero values (e.g. nil pointers).
Example ¶
package main import ( "fmt" "github.com/GodsBoss/g/optional" ) func main() { messages := map[string]string{ "departure": "Goodbye!", } optional. MapItem(messages, "departure"). Invoke( func(s string) { fmt.Println(s) }, ) fmt.Println( optional.IsEmpty( optional.MapItem(messages, "arrival"), ), ) }
Output: Goodbye! true
func NewEmpty ¶
NewEmpty creates an empty optional value. The returned value is immutable, i.e. cannot be changed to contain a value.
func NewWithItem ¶
NewWithItem creates an optional value that actually wraps an item. The returned value is immutable, i.e. cannot be changed to wrap a different value or no value at all.
func Pointer ¶
Pointer wraps a pointer into an optional value. nil pointers become empty values, else a value containing an item is returned.
Example (Nil) ¶
package main import ( "fmt" "github.com/GodsBoss/g/optional" ) func main() { var ptr *int value := optional.Pointer(ptr) fmt.Println(optional.HasItem(value)) }
Output: false
Example (Nonnil) ¶
package main import ( "fmt" "github.com/GodsBoss/g/optional" ) func main() { s := "Hello!" value := optional.Pointer(&s) if item, ok := optional.GetItem(value); ok { fmt.Println(*item) } }
Output: Hello!
func SliceItem ¶
SliceItem takes a slice and an index, returning an empty value if the index is out of bounds for the slice, and the corresponding item for that index otherwise. Only checks whether the index is in range and may happily wrap zero values (e.g. nil pointers).
Example ¶
package main import ( "fmt" "github.com/GodsBoss/g/optional" ) func main() { items := []string{ "foo", "bar", "baz", } optional. SliceItem(items, 1). Invoke( func(s string) { fmt.Println(s) }, ) fmt.Println( optional.IsEmpty( optional.SliceItem(items, -1), ), ) fmt.Println( optional.IsEmpty( optional.SliceItem(items, 8), ), ) }
Output: bar true true