Documentation ¶
Overview ¶
Package linq is a data manipulation library inspired by .Net Linq.
See the Catalog for a detailed functional overview of the library.
Usage ¶
// Sample usage linq.From(1, 2, 3, 4, 5).Where(func(i int) bool { return i%2 == 0 })
Caveats ¶
Because Go doesn't support generic methods, many functions are expressed as global functions. E.g:
// Not allowed linq.From(1, 2, 3, 4, 5).Select(func(i int) int { return i * i }) // OK linq.Select(linq.From(1, 2, 3, 4, 5), (func(i int) int { return i * i }))
Unfortunately, there are no clean work-arounds. You may wish to use a dot-import to ease the pain a little:
import . "github.com/linqgo/linq" ... Select(From(1, 2, 3, 4, 5), (func(i int) int { return i * i }))
In case your preferred style is to always use global functions, all Query methods are also available as global functions. An added benefit is that free functions can often be used as callbacks to other algorithms.
Comparison to .Net Linq ¶
The library implements almost all the methods in the .Net Enumerable class. The only exceptions are:
- AsEnumerable: not relevant to this library
- Cast: doesn't map cleanly to Go's type system.
On the flip side, this library implements a number of methods not provided by .Net.
Index ¶
- func AggregateSeed[T, A any](q Query[T], seed A, agg func(a A, t T) A) A
- func All[T any](q Query[T], pred func(t T) bool) bool
- func Any[T any](q Query[T], pred func(t T) bool) bool
- func Contains[T comparable](q Query[T], t T) bool
- func Count[T any](q Query[T]) int
- func CountLimit[T any](q Query[T], limit int) int
- func CountLimitTrue[T any](q Query[T], limit int) (int, bool)
- func Deref[T any](t *T) T
- func Drain[T any](next Enumerator[T]) int
- func ElseNaN[R num.RealNumber](r Maybe[R]) R
- func Empty[T any](q Query[T]) bool
- func Equal[T comparable](a, b T) bool
- func False[T any](T) bool
- func Greater[T constraints.Ordered](a, b T) bool
- func Identity[T any](t T) T
- func Key[KeyVal KV[K, V], K, V any](kv KV[K, V]) K
- func Less[T constraints.Ordered](a, b T) bool
- func Longer[A, B any](a Query[A], b Query[B]) bool
- func LongerMap[K1, K2 comparable, V1, V2 any, M1 ~map[K1]V1, M2 ~map[K2]V2](a M1, b M2) bool
- func LongerSlice[T any](a, b []T) bool
- func MustToMap[T, U any, K comparable](q Query[T], sel func(t T) KV[K, U]) map[K]U
- func MustToMapKV[K comparable, V any](q Query[KV[K, V]]) map[K]V
- func Not[T any](pred func(T) bool) func(T) bool
- func NotEqual[T comparable](a, b T) bool
- func Pointer[T any](t T) *T
- func Prepend[T any](t ...T) func(q Query[T]) Query[T]
- func Scanner[T any](q Query[T]) func(p *T) bool
- func SequenceEqual[T comparable](a, b Query[T]) bool
- func SequenceEqualEq[T any](a, b Query[T], eq func(a, b T) bool) bool
- func SequenceGreater[T constraints.Ordered](a, b Query[T]) bool
- func SequenceGreaterComp[T any](a, b Query[T], less func(a, b T) bool) bool
- func SequenceLess[T constraints.Ordered](a, b Query[T]) bool
- func SequenceLessComp[T any](a, b Query[T], less func(a, b T) bool) bool
- func Shorter[A, B any](a Query[A], b Query[B]) bool
- func ShorterMap[K1, K2 comparable, V1, V2 any, M1 ~map[K1]V1, M2 ~map[K2]V2](a M1, b M2) bool
- func ShorterSlice[T any](a, b []T) bool
- func StringsCommaAnd[S ~string](q Query[S], comma, and S) S
- func StringsJoin[S ~string](q Query[S], sep S) S
- func Sum[R num.Number](q Query[R]) R
- func SwapArgs[A, B, C any](f func(a A, b B) C) func(B, A) C
- func ToMap[T, U any, K comparable](q Query[T], sel func(t T) KV[K, U]) (map[K]U, error)
- func ToMapKV[K comparable, V any](q Query[KV[K, V]]) (map[K]V, error)
- func ToSlice[T any](q Query[T]) []T
- func ToString(q Query[rune]) string
- func True[T any](T) bool
- func Unzip[T, R, S any](q Query[T], unzip func(t T) (R, S)) (Query[R], Query[S])
- func UnzipKV[K, V any](q Query[KV[K, V]]) (Query[K], Query[V])
- func Value[KeyVal KV[K, V], K, V any](kv KV[K, V]) V
- func Zero[U, T any](T) U
- type Array
- type Delta
- type Enumerator
- type Error
- type Getter
- type KV
- type Maybe
- func Aggregate[T any](q Query[T], agg func(a, b T) T) Maybe[T]
- func Average[R num.RealNumber](q Query[R]) Maybe[R]
- func ElementAt[T any](q Query[T], i int) Maybe[T]
- func FastCount[T any](q Query[T]) Maybe[int]
- func FastElementAt[T any](q Query[T], i int) Maybe[T]
- func FastLast[T any](q Query[T]) Maybe[T]
- func FastLonger[A, B any](a Query[A], b Query[B]) Maybe[bool]
- func FastShorter[A, B any](a Query[A], b Query[B]) Maybe[bool]
- func First[T any](q Query[T]) Maybe[T]
- func FirstComp[T any](q Query[T], precedes func(a, b T) bool) Maybe[T]
- func Last[T any](q Query[T]) Maybe[T]
- func LastComp[T any](q Query[T], precedes func(a, b T) bool) Maybe[T]
- func Max[R constraints.Ordered](q Query[R]) Maybe[R]
- func MaxBy[T any, R constraints.Ordered](q Query[T], key func(T) R) Maybe[T]
- func MaybeFlatMap[T, U any](m Maybe[T], f func(T) Maybe[U]) Maybe[U]
- func Min[R constraints.Ordered](q Query[R]) Maybe[R]
- func MinBy[T any, K constraints.Ordered](q Query[T], key func(T) K) Maybe[T]
- func NewMaybe[T any](t T, valid bool) Maybe[T]
- func No[T any]() Maybe[T]
- func Single[T any](q Query[T]) Maybe[T]
- func Some[T any](t T) Maybe[T]
- type Query
- func Append[T any](q Query[T], t ...T) Query[T]
- func Chunk[T any](q Query[T], size int) Query[Query[T]]
- func ChunkSlices[T any](q Query[T], size int) Query[[]T]
- func Concat[T any](queries ...Query[T]) Query[T]
- func DefaultIfEmpty[T any](q Query[T], alt T) Query[T]
- func Distinct[T comparable](q Query[T]) Query[T]
- func DistinctBy[T any, U comparable](q Query[T], sel func(t T) U) Query[T]
- func Every[T any](q Query[T], n int) Query[T]
- func EveryFrom[T any](q Query[T], start, n int) Query[T]
- func Except[T comparable](a, b Query[T]) Query[T]
- func ExceptBy[T any, K comparable](a Query[T], b Query[K], key func(t T) K) Query[T]
- func Flatten[T any](q Query[Query[T]]) Query[T]
- func FlattenSlices[T any](q Query[[]T]) Query[T]
- func From[T any](t ...T) Query[T]
- func FromArray[T any](a Array[T]) Query[T]
- func FromByteReader(r io.ByteReader) Query[byte]
- func FromChannel[T any](c <-chan T) Query[T]
- func FromGetter[T any](get Getter[T]) Query[T]
- func FromMap[K comparable, V any, M ~map[K]V](m M) Query[KV[K, V]]
- func FromRuneReader(r io.RuneReader) Query[rune]
- func FromScanner(s *bufio.Scanner) Query[[]byte]
- func FromScannerString(r *bufio.Scanner) Query[string]
- func FromString(s string) Query[rune]
- func GroupBy[T any, K comparable](q Query[T], key func(t T) K) Query[KV[K, Query[T]]]
- func GroupBySelect[T, U any, K comparable](q Query[T], sel func(t T) KV[K, U]) Query[KV[K, Query[U]]]
- func GroupBySelectSlices[T, U any, K comparable](q Query[T], sel func(t T) KV[K, U]) Query[KV[K, []U]]
- func GroupBySlices[T any, K comparable](q Query[T], key func(t T) K) Query[KV[K, []T]]
- func GroupJoin[Outer, Inner, Result any, Key comparable](outer Query[Outer], inner Query[Inner], outerKey func(Outer) Key, ...) Query[Result]
- func Index[T any](q Query[T]) Query[KV[int, T]]
- func IndexFrom[T any](q Query[T], start int) Query[KV[int, T]]
- func Intersect[T comparable](a, b Query[T]) Query[T]
- func IntersectBy[T, K comparable](a Query[T], b Query[K], key func(t T) K) Query[T]
- func Iota[I num.RealNumber]() Query[I]
- func Iota1[I num.RealNumber](stop I) Query[I]
- func Iota2[I num.RealNumber](start, stop I) Query[I]
- func Iota3[I num.RealNumber](start, stop, step I) Query[I]
- func Join[A, B, R any, K comparable](a Query[A], b Query[B], selKeyA func(a A) K, selKeyB func(b B) K, ...) Query[R]
- func Memoize[T any](q Query[T]) Query[T]
- func NewQuery[T any](i func() Enumerator[T], options ...QueryOption[T]) Query[T]
- func None[T any]() Query[T]
- func OfType[U, T any](q Query[T]) Query[U]
- func Order[T constraints.Ordered](q Query[T]) Query[T]
- func OrderBy[T any, K constraints.Ordered](q Query[T], key func(t T) K) Query[T]
- func OrderByDesc[T any, K constraints.Ordered](q Query[T], key func(t T) K) Query[T]
- func OrderByKey[K constraints.Ordered, V any](q Query[KV[K, V]]) Query[KV[K, V]]
- func OrderByKeyDesc[K constraints.Ordered, V any](q Query[KV[K, V]]) Query[KV[K, V]]
- func OrderComp[T any](q Query[T], lesses ...func(a, b T) bool) Query[T]
- func OrderCompDesc[T any](q Query[T], lesses ...func(a, b T) bool) Query[T]
- func OrderDesc[T constraints.Ordered](q Query[T]) Query[T]
- func Pairwise[T any](q Query[T]) Query[KV[T, T]]
- func Pipe[T, U any](q Query[T], enum func(next Enumerator[T]) Enumerator[U], ...) Query[U]
- func PipeOneToOne[T, U any](q Query[T], selfunc func() func(t T) U, options ...QueryOption[U]) Query[U]
- func PowerSet[T any](q Query[T]) Query[Query[T]]
- func Repeat[T any, I constraints.Integer](value T, count I) Query[T]
- func RepeatForever[T any](value T) Query[T]
- func Reverse[T any](q Query[T]) Query[T]
- func Sample[T any](q Query[T], p float64) Query[T]
- func SampleSeed[T any](q Query[T], p float64, seed int64) Query[T]
- func Select[T, U any](q Query[T], sel func(t T) U) Query[U]
- func SelectKeys[K, V any](q Query[KV[K, V]]) Query[K]
- func SelectMany[T, U any](q Query[T], project func(T) Query[U]) Query[U]
- func SelectValues[K, V any](q Query[KV[K, V]]) Query[V]
- func Skip[T any](q Query[T], skip int) Query[T]
- func SkipLast[T any](q Query[T], skip int) Query[T]
- func SkipWhile[T any](q Query[T], pred func(t T) bool) Query[T]
- func Slide[T any](q Query[T], slideIn bool, expired func(older, current T) bool) Query[Delta[T]]
- func SlideAll[T any](q Query[T]) Query[Delta[T]]
- func SlideFixed[T any](q Query[T], windowSize int, slideIn bool) Query[Delta[T]]
- func SlideTime[Time num.RealNumber, T any](q Query[KV[Time, T]], expiryAge Time, slideIn bool) Query[Delta[KV[Time, T]]]
- func Take[T any](q Query[T], take int) Query[T]
- func TakeLast[T any](q Query[T], take int) Query[T]
- func TakeWhile[T any](q Query[T], pred func(t T) bool) Query[T]
- func Then[T constraints.Ordered](q Query[T]) Query[T]
- func ThenBy[T any, K constraints.Ordered](q Query[T], key func(t T) K) Query[T]
- func ThenByDesc[T any, K constraints.Ordered](q Query[T], key func(t T) K) Query[T]
- func ThenByKey[K constraints.Ordered, V any](q Query[KV[K, V]]) Query[KV[K, V]]
- func ThenByKeyDesc[K constraints.Ordered, V any](q Query[KV[K, V]]) Query[KV[K, V]]
- func ThenComp[T any](q Query[T], lesses ...func(a, b T) bool) Query[T]
- func ThenCompDesc[T any](q Query[T], lesses ...func(a, b T) bool) Query[T]
- func ThenDesc[T constraints.Ordered](q Query[T]) Query[T]
- func Union[T comparable](a, b Query[T]) Query[T]
- func Where[T any](q Query[T], pred func(t T) bool) Query[T]
- func Zip[A, B, R any](a Query[A], b Query[B], zip func(a A, b B) R) Query[R]
- func ZipKV[K, V any](k Query[K], v Query[V]) Query[KV[K, V]]
- func (q Query[T]) Aggregate(agg func(a, b T) T) Maybe[T]
- func (q Query[T]) AggregateSeed(seed T, agg func(a, b T) T) T
- func (q Query[T]) All(pred func(t T) bool) bool
- func (q Query[T]) Any(pred func(t T) bool) bool
- func (q Query[T]) Append(t ...T) Query[T]
- func (q Query[T]) Concat(r Query[T]) Query[T]
- func (q Query[T]) Count() int
- func (q Query[T]) CountLimit(limit int) int
- func (q Query[T]) CountLimitTrue(limit int) (int, bool)
- func (q Query[T]) DefaultIfEmpty(alt T) Query[T]
- func (q Query[T]) ElementAt(i int) Maybe[T]
- func (q Query[T]) Empty() bool
- func (q Query[T]) Enumerator() Enumerator[T]
- func (q Query[T]) Every(n int) Query[T]
- func (q Query[T]) EveryFrom(start, n int) Query[T]
- func (q Query[T]) FastCount() Maybe[int]
- func (q Query[T]) FastElementAt(i int) Maybe[T]
- func (a Query[T]) FastLonger(b Query[T]) Maybe[bool]
- func (a Query[T]) FastShorter(b Query[T]) Maybe[bool]
- func (q Query[T]) First() Maybe[T]
- func (q Query[T]) FirstComp(precedes func(a, b T) bool) Maybe[T]
- func (q Query[T]) Last() Maybe[T]
- func (q Query[T]) LastComp(precedes func(a, b T) bool) Maybe[T]
- func (q Query[T]) Longer(r Query[T]) bool
- func (q Query[T]) Memoize() Query[T]
- func (q Query[T]) OneShot() bool
- func (q Query[T]) OrderComp(lesses ...func(a, b T) bool) Query[T]
- func (q Query[T]) OrderCompDesc(lesses ...func(a, b T) bool) Query[T]
- func (q Query[T]) Prepend(t ...T) Query[T]
- func (q Query[T]) Reverse() Query[T]
- func (q Query[T]) Sample(p float64) Query[T]
- func (q Query[T]) SampleSeed(p float64, seed int64) Query[T]
- func (q Query[T]) Scanner() func(p *T) bool
- func (q Query[T]) Select(sel func(t T) T) Query[T]
- func (q Query[T]) SequenceEqualEq(r Query[T], eq func(a, b T) bool) bool
- func (q Query[T]) SequenceGreaterComp(r Query[T], less func(a, b T) bool) bool
- func (q Query[T]) SequenceLessComp(r Query[T], less func(a, b T) bool) bool
- func (q Query[T]) Shorter(r Query[T]) bool
- func (q Query[T]) Single() Maybe[T]
- func (q Query[T]) Skip(skip int) Query[T]
- func (q Query[T]) SkipLast(skip int) Query[T]
- func (q Query[T]) SkipWhile(pred func(t T) bool) Query[T]
- func (q Query[T]) Take(count int) Query[T]
- func (q Query[T]) TakeLast(count int) Query[T]
- func (q Query[T]) TakeWhile(pred func(t T) bool) Query[T]
- func (q Query[T]) ThenComp(lesses ...func(a, b T) bool) Query[T]
- func (q Query[T]) ThenCompDesc(lesses ...func(a, b T) bool) Query[T]
- func (q Query[T]) ToArray() Array[T]
- func (q Query[T]) ToGetter() Getter[T]
- func (q Query[T]) ToSlice() []T
- func (q Query[T]) Where(pred func(t T) bool) Query[T]
- type QueryOption
- func ComputedFastCountOption[T any](count int, compute func(count int) int) QueryOption[T]
- func FastCountIfEmptyOption[T any](count int) QueryOption[T]
- func FastCountOption[T any](count int) QueryOption[T]
- func FastGetOption[T any](get Getter[T]) QueryOption[T]
- func LesserOption[T any](lesser lesserFunc[T]) QueryOption[T]
- func OneShotOption[T any](oneShot bool) QueryOption[T]
Constants ¶
This section is empty.
Variables ¶
This section is empty.
Functions ¶
func AggregateSeed ¶
AggregateSeed applies an aggregator function to the elements of q, using seed as the initial value, and returns the aggregated result.
func Contains ¶
func Contains[T comparable](q Query[T], t T) bool
Contains returns true if and only if t is an element in q.
func CountLimit ¶
CountLimit returns a limited count, c, such that min(limit, Count(q)) <= c <= Count(q). This is useful for learning something about the size of the input without necessarily consuming it. One example is activating pagination controls for a result with at least 11 elements.
If the query has a FastCount(), the return value is the true count.
func CountLimitTrue ¶ added in v0.11.0
CountLimitTrue returns a limited count, c, such that min(limit, Count(q)) <= c <= Count(q). This is useful for learning something about the size of the input without necessarily consuming it. One example is activating pagination controls for a result with at least 11 elements.
If the query has a FastCount(), the return value is the true count.
The second return value is true if the returned count is the true count.
func Drain ¶ added in v0.11.0
func Drain[T any](next Enumerator[T]) int
Drain consumes next and returns the number of elements consumed.
func ElseNaN ¶ added in v0.12.0
func ElseNaN[R num.RealNumber](r Maybe[R]) R
func LongerMap ¶
func LongerMap[K1, K2 comparable, V1, V2 any, M1 ~map[K1]V1, M2 ~map[K2]V2](a M1, b M2) bool
LongerMap returns len(a) > len(b).
func MustToMap ¶
func MustToMap[T, U any, K comparable](q Query[T], sel func(t T) KV[K, U]) map[K]U
MustToMap converts a query to a map, with sel providing key/value pairs. If any keys are duplicated, MustToMap will panic.
func MustToMapKV ¶
func MustToMapKV[K comparable, V any](q Query[KV[K, V]]) map[K]V
MustToMapKV converts a Query[KV[...]] to a map. If any keys are duplicated, MustToMapKV will panic.
func Prepend ¶
Prepend returns a query with the elements of t followed by the elements of q.
So that t... args appear before q, Prepend takes just t and returns a func that takes q.
func Scanner ¶ added in v0.16.0
Scanner returns a function that scans entries from q, setting the passed pointer parameter to each element and returning true until it runs out of elements. Then it returns false.
func SequenceEqual ¶
func SequenceEqual[T comparable](a, b Query[T]) bool
SequenceEqual returns true if a and b contain the same number of elements and each sequential element from a equals the corresponding sequential element from b.
func SequenceEqualEq ¶ added in v0.11.0
SequenceEqualEq returns true if a and b contain the same number of elements and each sequential element from a equals the corresponding sequential element from b. The eq function is called to determine equality.
func SequenceGreater ¶ added in v0.9.0
func SequenceGreater[T constraints.Ordered](a, b Query[T]) bool
SequenceGreater compares elements pairwise from a and b in sequence order and returns true if and only if one of the following occurs:
- Two elements differ and the element from a is greater than the one from b.
- Query b runs out of elements before a.
This is known as lexicographical sort and is equivalent to the > operator on strings.
func SequenceGreaterComp ¶ added in v0.11.0
SequenceGreaterComp compares elements pairwise from a and b in sequence order and returns true if and only if one of the following occurs:
- less(bElem, aElem) returns true. (Note the order of parameters.)
- Query b runs out of elements before a.
This is known as lexicographical sort and is equivalent to the < operator on strings.
func SequenceLess ¶
func SequenceLess[T constraints.Ordered](a, b Query[T]) bool
SequenceLess compares elements pairwise from a and b in sequence order and returns true if and only if one of the following occurs:
- Two elements differ and the element from a is less than the one from b.
- Query a runs out of elements before b.
This is known as lexicographical sort and is equivalent to the < operator on strings.
func SequenceLessComp ¶ added in v0.11.0
SequenceLessComp compares elements pairwise from a and b in sequence order and returns true if and only if one of the following occurs:
- less(aElem, bElem) returns true.
- Query a runs out of elements before b.
This is known as lexicographical sort and is equivalent to the < operator on strings.
func ShorterMap ¶
func ShorterMap[K1, K2 comparable, V1, V2 any, M1 ~map[K1]V1, M2 ~map[K2]V2](a M1, b M2) bool
ShorterMap returns len(a) < len(b).
func StringsCommaAnd ¶ added in v0.17.0
func StringsJoin ¶ added in v0.17.0
StringsJoin joins strings with a separator.
func Sum ¶
Sum returns the sum of the num.Numbers in q or 0 if q is empty.
This function is equivalent to "github.com/linqgo/linq/stats".Sum. It is retained here for parity with .Net's Enumerable class.
func SwapArgs ¶ added in v0.11.0
func SwapArgs[A, B, C any](f func(a A, b B) C) func(B, A) C
SwapArgs returns a function that swaps the parameters of the specified function.
func ToMap ¶
func ToMap[T, U any, K comparable](q Query[T], sel func(t T) KV[K, U]) (map[K]U, error)
ToMap converts a query to a map, with sel providing key/value pairs. If any keys are duplicated, ToMap will return an error.
func ToMapKV ¶
func ToMapKV[K comparable, V any](q Query[KV[K, V]]) (map[K]V, error)
ToMapKV converts a Query[KV[...]] to a map. If any keys are duplicated, ToMap will return an error.
func Unzip ¶
Unzip unzips a single query into two queries whose elements come from the R and S outputs of the specified unzip function.
The following example outputs two queries, one containing the input numbers divided by n and the other containing the remainder.
func DivMod(q Query[int], n int) (div, mod Query[int]) { return Unzip(q, func(i int) (int, int) { return i / n, i % n }) }
Types ¶
type Array ¶ added in v0.12.0
func ArrayFromLenGet ¶ added in v0.12.0
type Enumerator ¶
Enumerator is a function type that enumerates values. To produce a value, it returns the value and true. When there are no more values to produce, it returns an indeterminate value and false.
type Getter ¶ added in v0.12.0
func ArrayGetter ¶ added in v0.12.0
ArrayGetter returns a Getter for an Array.
func LenGetGetter ¶ added in v0.12.0
LenGetGetter returns a Getter for a len/get pair.
type Maybe ¶ added in v0.12.0
type Maybe[T any] struct { // contains filtered or unexported fields }
func Aggregate ¶
Aggregate applies an aggregator function to the elements of q and returns the aggregated result or !ok if q is empty.
func Average ¶
func Average[R num.RealNumber](q Query[R]) Maybe[R]
Average returns the arithmetic mean of the numbers in q or ok = false if q is empty.
This function is equivalent to "github.com/linqgo/linq/stats".Mean. It is retained here for parity with .Net's Enumerable class.
func FastCount ¶
FastCount returns the number of elements in q if it can be computed in O(1) time, otherwise the second return value is false.
func FastElementAt ¶ added in v0.12.0
FastElementAt returns the element at position i or !ok if there is no element i or element i cannot be accessed in O(1) time.
func FastLast ¶ added in v0.12.0
FastLast returns the last element or !ok if q is empty or the last element cannot be accessed in O(1) time.
func FastLonger ¶ added in v0.11.0
FastLonger returns true if and only if a has more elements than b and this can be determined in O(1) time, otherwise returns ok = false.
func FastShorter ¶ added in v0.11.0
FastShorter returns true if and only if a has fewer elements than b and this can be determined in O(1) time, otherwise returns ok = false.
func FirstComp ¶ added in v0.11.0
FirstComp returns the element in q that precedes every other element or ok = false if q is empty.
func LastComp ¶ added in v0.11.0
LastComp returns the element in q that precedes every other element or ok = false if q is empty.
func Max ¶
func Max[R constraints.Ordered](q Query[R]) Maybe[R]
Max returns the highest number in q or ok=false if q is empty.
func MaxBy ¶
func MaxBy[T any, R constraints.Ordered](q Query[T], key func(T) R) Maybe[T]
MaxBy returns the element in q with the highest key or ok = false if q is empty.
func MaybeFlatMap ¶ added in v0.14.0
func Min ¶
func Min[R constraints.Ordered](q Query[R]) Maybe[R]
Min returns the highest number in q or ok=false if q is empty.
type Query ¶
type Query[T any] struct { // contains filtered or unexported fields }
Query represents a query that can be enumerated. This is the main Linq object, with many methods defined against it. Most Linq functions take and return instances of this type.
func ChunkSlices ¶
ChunkSlices returns the elements of q in slices of the specified size.
func Concat ¶
Concat returns the concatenation of queries. Enumerating it enumerates the elements of each Query in turn.
func DefaultIfEmpty ¶
DefaultIfEmpty returns q if not empty, otherwise it returns a query containing alt.
func Distinct ¶
func Distinct[T comparable](q Query[T]) Query[T]
Distinct contains elements from an query with duplicates removed.
func DistinctBy ¶
func DistinctBy[T any, U comparable](q Query[T], sel func(t T) U) Query[T]
DistinctBy contains elements from a query with duplicates removed. A selector function produces values for comparison. E.g. for case-insensitive deduplication:
DistinctBy(names, strings.ToUpper)
func EveryFrom ¶
Every returns a query that contains every nth element from q, starting at the start-th element.
func Except ¶
func Except[T comparable](a, b Query[T]) Query[T]
Except returns all elements of a except those also found in b.
func ExceptBy ¶
func ExceptBy[T any, K comparable]( a Query[T], b Query[K], key func(t T) K, ) Query[T]
ExceptBy returns all elements of a except those whose key is found in b.
func FlattenSlices ¶
func FromByteReader ¶
func FromByteReader(r io.ByteReader) Query[byte]
FromByteReader returns a query containing bytes read from r. Hint: use a bufio.Reader to wrap an io.Reader in an io.ByteReader.
The returned query is not replayable. Use (Query).Memoize() if you need a replayable query.
func FromChannel ¶
FromChannel returns a query that reads values from c.
The returned query is not replayable. Use (Query).Memoize() if you need a replayable query.
func FromGetter ¶ added in v0.12.0
func FromMap ¶
func FromMap[K comparable, V any, M ~map[K]V](m M) Query[KV[K, V]]
FromMap returns a query with KVs sourced from m.
func FromRuneReader ¶
func FromRuneReader(r io.RuneReader) Query[rune]
FromRuneReader returns a query containing runes read from r. Hint: use a bufio.Reader to wrap an io.Reader in an io.RuneReader.
The returned query is not replayable. Use (Query).Memoize() if you need a replayable query.
func FromScanner ¶
FromScanner reads a query containing []byte tokens read from s. Hint: use (Scanner).Split() to control how the input stream is tokenized.
func FromScannerString ¶
FromScannerString reads a query containing string tokens read from s. Hint: use (Scanner).Split() to control how the input stream is tokenized.
func FromString ¶
FromString returns a Query[rune] with the runes from s.
func GroupBy ¶
GroupBy returns a Query[KV[K, Query[T]]] with elements from q grouped using the specified key function.
func GroupBySelect ¶
func GroupBySelect[T, U any, K comparable]( q Query[T], sel func(t T) KV[K, U], ) Query[KV[K, Query[U]]]
GroupBySelect returns a Query[KV[K, Query[T]]] with elements from q grouped using the specified sel function, which produces a key/value pair for each source element.
func GroupBySelectSlices ¶
func GroupBySelectSlices[T, U any, K comparable]( q Query[T], sel func(t T) KV[K, U], ) Query[KV[K, []U]]
GroupBySelectSlices returns a Query[KV[K, []T]] with elements from q grouped using the specified sel function, which produces a key/value pair for each source element.
func GroupBySlices ¶
func GroupBySlices[T any, K comparable]( q Query[T], key func(t T) K, ) Query[KV[K, []T]]
GroupBySlices returns a Query[KV[K, []T]] with elements from q grouped using the specified key function.
func Intersect ¶
func Intersect[T comparable](a, b Query[T]) Query[T]
Intersect returns the set intersection of a and b.
func IntersectBy ¶
func IntersectBy[T, K comparable]( a Query[T], b Query[K], key func(t T) K, ) Query[T]
IntersectBy returns the set intersection of a and b.
func Iota ¶
func Iota[I num.RealNumber]() Query[I]
Iota returns a query with all integers from 0 up.
func Iota1 ¶
func Iota1[I num.RealNumber](stop I) Query[I]
Iota1 returns a query with all integers in the range [0, stop).
func Iota2 ¶
func Iota2[I num.RealNumber](start, stop I) Query[I]
Iota2 returns a query with all integers in the range [start, stop).
func Iota3 ¶
func Iota3[I num.RealNumber](start, stop, step I) Query[I]
Iota3 returns a query with every step-th integer in the range [start, stop).
func Join ¶
func Join[A, B, R any, K comparable]( a Query[A], b Query[B], selKeyA func(a A) K, selKeyB func(b B) K, selResult func(a A, b B) R, ) Query[R]
Join returns the join of q1 and q2. selKey1 and selKey2 produce keys from elements of q1 and q2, respectively. Element pairs with the same key are passed to selResult to produce output elements.
func Memoize ¶
Memoize caches the elements of q. It returns a query that contains the same elements as q, but, in the process of enumerating it, remembers the sequence of values seen and ensures that every enumeration yields the same sequence.
func NewQuery ¶
func NewQuery[T any](i func() Enumerator[T], options ...QueryOption[T]) Query[T]
NewQuery returns a new query based on a function that returns enumerators.
func OrderByDesc ¶
func OrderByDesc[T any, K constraints.Ordered](q Query[T], key func(t T) K) Query[T]
func OrderByKey ¶ added in v0.19.0
func OrderByKeyDesc ¶ added in v0.19.0
func OrderCompDesc ¶ added in v0.9.0
func Pipe ¶
func Pipe[T, U any]( q Query[T], enum func(next Enumerator[T]) Enumerator[U], options ...QueryOption[U], ) Query[U]
Pipe returns a Query that transforms an input query by transforming its enumerator. If q is one-shot then the returned Query is assumed to be one-shot.
func PipeOneToOne ¶ added in v0.12.0
func PipeOneToOne[T, U any]( q Query[T], selfunc func() func(t T) U, options ...QueryOption[U], ) Query[U]
PipeOneToOne returns a Pipe with a bijection from input to output elements.
func Repeat ¶
func Repeat[T any, I constraints.Integer](value T, count I) Query[T]
Repeat returns a query with value repeated count times.
func RepeatForever ¶
RepeatForever returns a query with value repeated forever.
func Sample ¶
Sample returns a query that randomly samples each element in q with probability p. The returned query will deterministically sample values at the same intervals each time an enumerator is requested. This is not the case across calls to Sample.
func SampleSeed ¶
SampleSeed returns a query that randomly samples each element in q with probability p.
The seed allows for deterministic results. Multiple invokations of SampleSeed with the same seed will return a query that samples values at the same intervals.
func SelectKeys ¶
SelectKeys returns a query containing the keys from a query of KVs.
func SelectMany ¶
SelectMany projects each element of q to a subquery and flattens the subqueries into a single query.
func SelectValues ¶
SelectValues returns a query containing the values from a query of KVs.
func Slide ¶ added in v0.14.0
Slide implements a sliding window. All output elements represent windows over the input elements. Windows are represented as Deltas indicating which elements are entering and exiting the window as it slides along.
Maximality is an important concept in the discussion below. A maximal window is one for which expired(tail, head) is false, but which would become true if the window were extended at either end. Put another way, a window is maximal if it has no expired elements but becomes invalid if grown.
Initial output is determined by the slideIn parameter. As the input is read, the sliding window grows by one element for each input element. Thereafter, every output window is maximal. If the slideIn parameter is true, the initial non-maximal windows will be output. If false, they will be skipped.
The maximality criterion implies that all output windows bar the initial ones satisfy len(in) > 0 && len(out) > 0. This is because adding elements to a maximal window without removing any would necessarily produce an invalid window, whereas removing elements from a maximal window without adding any would necessarily produce a non-maximal window.
For some windows, len(in) > 1 && len(out) > 1, which means that the window has slid forward more than one step. How this might happen can be seen when considering how a maximal window is advanced. The first step is to remove stale elements from the tail until it is possible to add new elements to the head. This could require the removal of more than element. Once enough elements are removed, the window must be grown until it is maximal again, and this could in turn require more than one addition. The example below illustrates one such scenario. The second delta represents the window sliding from {1, 2, 3} to {3, 5, 5}. This skips {2, 3, 5}, which contains expired element 2 and is thus invalid. In other scenarios, skipped windows will be valid but non-maximal.
Example:
Slide( linq.From(1, 2, 3, 5, 5, 6, 7, 8), func(tail, head int) bool { return tail < head - 2 }, ) // Window: {1,2,3} {3,5,5} {5,5,6,7} {6,7,8} // Delta: ⁺{1,2,3} ⁻{1,2}⁺{5,5} ⁻{3}⁺{6,7} ⁻{5,5}⁺{8}
func SlideAll ¶ added in v0.14.0
SlideAll implements an ever-expanding window of all elements seen to date.
func SlideFixed ¶ added in v0.14.0
SlideFixed implements a sliding window of at most windowSize elements.
func SlideTime ¶ added in v0.14.0
func SlideTime[Time num.RealNumber, T any]( q Query[KV[Time, T]], expiryAge Time, slideIn bool, ) Query[Delta[KV[Time, T]]]
SlideTime implements a sliding window of elements that are younger than the specified expiryAge.
func ThenByDesc ¶
func ThenByDesc[T any, K constraints.Ordered](q Query[T], key func(t T) K) Query[T]
func ThenByKeyDesc ¶ added in v0.19.0
func ThenCompDesc ¶ added in v0.9.0
func Union ¶
func Union[T comparable](a, b Query[T]) Query[T]
Union returns the set union of a and b.
func Zip ¶
Zip zips the elements pairwise from a and b into a single query, using the zip function to produce output elements.
func (Query[T]) Aggregate ¶
Aggregate applies an aggregator function to the elements of q and returns the aggregated result or !ok if q is empty.
func (Query[T]) AggregateSeed ¶
func (q Query[T]) AggregateSeed(seed T, agg func(a, b T) T) T
AggregateSeed applies an aggregator function to the elements of q, using seed as the initial value, and returns the aggregated result.
Use the global AggregateSeed function if the seed and result are not of type T (e.g., concatenate a Query[int] into a string).
func (Query[T]) All ¶
All returns true if pred returns true for all elements in q, including if q is empty.
func (Query[T]) Append ¶
Append returns a query with the elements of q followed by the elements of t.
func (Query[T]) Concat ¶
Concat returns the concatenation of q and r. Enumerating it enumerates the elements of each Query in turn.
func (Query[T]) CountLimit ¶
CountLimit returns a limited count, c, such that min(limit, Count(q)) <= c <= Count(q). This is useful for learning something about the size of the input without necessarily consuming it. One example is activating pagination controls for a result with at least 11 elements.
If the query has a FastCount(), the return value is the true count.
func (Query[T]) CountLimitTrue ¶ added in v0.11.0
CountLimitTrue returns a limited count, c, such that min(limit, Count(q)) <= c <= Count(q). This is useful for learning something about the size of the input without necessarily consuming it. One example is activating pagination controls for a result with at least 11 elements.
If the query has a FastCount(), the return value is the true count.
The second return value is true if the returned count is the true count.
func (Query[T]) DefaultIfEmpty ¶
DefaultIfEmpty returns q if not empty, otherwise it returns a query containing alt.
func (Query[T]) ElementAt ¶
ElementAt returns the element at position i or !ok if there is no element i.
func (Query[T]) Enumerator ¶
func (q Query[T]) Enumerator() Enumerator[T]
Enumerator returns an enumerator for q.
func (Query[T]) EveryFrom ¶
Every returns a query that contains every nth element from q, starting at the start-th element.
func (Query[T]) FastCount ¶
FastCount returns the number of elements in q if it can be computed in O(1) time, otherwise the second return value is false.
func (Query[T]) FastElementAt ¶ added in v0.12.0
FastElementAt returns the element at position i or !ok if there is no element i or the element cannot be accessed in O(1) time.
func (Query[T]) FastLonger ¶ added in v0.11.0
FastLonger returns true if and only if a has more elements than b and this can be determined in O(1) time, otherwise returns ok = false.
func (Query[T]) FastShorter ¶ added in v0.11.0
FastShorter returns true if and only if a has fewer elements than b and this can be determined in O(1) time, otherwise returns ok = false.
func (Query[T]) FirstComp ¶ added in v0.11.0
FirstComp returns the element in q that precedes every other element or ok = false if q is empty.
func (Query[T]) LastComp ¶ added in v0.11.0
LastComp returns the element in q that precedes every other element or ok = false if q is empty.
func (Query[T]) Longer ¶ added in v0.11.0
Longer returns true if and only if q has more elements than r.
func (Query[T]) Memoize ¶
Memoize caches the elements of q. It returns a query that contains the same elements as q, but, in the process of enumerating it, remembers the sequence of values seen and ensures that every enumeration yields the same sequence.
func (Query[T]) OrderCompDesc ¶ added in v0.11.0
func (Query[T]) Prepend ¶
Prepend returns a query with the elements of t followed by the elements of q.
Be careful! Prepend puts the tail arguments, t, in front of q. To avoid confusion and bugs, consider using the corresponding global Prepend function.
func (Query[T]) Sample ¶
Sample returns a query that randomly samples each element in q with probability p. The returned query will deterministically sample values at the same intervals each time an enumerator is requested. This is not the case for multiple calls to Sample for the same q.
func (Query[T]) SampleSeed ¶
SampleSeed returns a query that randomly samples each element in q with probability p.
The seed allows for deterministic results. Multiple invokations of SampleSeed with the same seed will return a query that samples values at the same intervals.
func (Query[T]) Select ¶ added in v0.11.0
Select returns a query with the elements of q transformed by sel.
Caveat: The output must be of the same type. For transforms to different types, use the corresponding free function.
func (Query[T]) SequenceEqualEq ¶ added in v0.11.0
SequenceEqualEq returns true if q and r contain the same number of elements and each sequential element from a equals the corresponding sequential element from b. The eq function is called to determine equality.
func (Query[T]) SequenceGreaterComp ¶ added in v0.11.0
SequenceGreaterComp compares elements pairwise from q and r in sequence order and returns true if and only if one of the following occurs:
- less(rElem, qElem) returns true. (Note the reversed parameters.)
- Query r runs out of elements before q.
This is known as lexicographical sort and is equivalent to the < operator on strings.
func (Query[T]) SequenceLessComp ¶ added in v0.11.0
SequenceLessComp compares elements pairwise from q and r in sequence order and returns true if and only if one of the following occurs:
- less(qElem, rElem) returns true.
- Query q runs out of elements before r.
This is known as lexicographical sort and is equivalent to the < operator on strings.
func (Query[T]) Shorter ¶ added in v0.11.0
Shorter returns true if and only if q has fewer elements than r.
func (Query[T]) SkipWhile ¶
SkipWhile returns a query that skips elements of q while pred returns true.
func (Query[T]) TakeWhile ¶
TakeWhile returns a query that takes elements of q while pred returns true.
func (Query[T]) ThenCompDesc ¶ added in v0.11.0
func (Query[T]) ToArray ¶ added in v0.12.0
ToArray returns an Array interface containing the elements of q.
func (Query[T]) ToGetter ¶ added in v0.12.0
ToGetter returns a Getter providing access to the elements of q.
type QueryOption ¶
func ComputedFastCountOption ¶
func ComputedFastCountOption[T any]( count int, compute func(count int) int, ) QueryOption[T]
func FastCountIfEmptyOption ¶
func FastCountIfEmptyOption[T any](count int) QueryOption[T]
FastCountIfEmptyOption is used when implementing a third-party Query. If an empty input query produces an empty output query, use FastCountIfEmptyOption to report a FastCount of 0 for the output query. This will be used by (Query).FastCount &co.
func FastCountOption ¶
func FastCountOption[T any](count int) QueryOption[T]
FastCountOption is used when implementing a third-party Query. If a query's count can be determined in O(1) time, the value may be supplied as a FastCountOption to NewQuery. This will be used by (Query).FastCount &co.
func FastGetOption ¶ added in v0.12.0
func FastGetOption[T any](get Getter[T]) QueryOption[T]
FastGetOption is used when implement a third-party Query. If any element can be accessed by index in O(1) time, the accessor may be supplied via this option.
func LesserOption ¶
func LesserOption[T any](lesser lesserFunc[T]) QueryOption[T]
func OneShotOption ¶
func OneShotOption[T any](oneShot bool) QueryOption[T]
OneShotOption is used when implementing a third-party Query. Some queries are consumed during enumeration and will thus be empty the second time you try to enumerate them (e.g., a query that reads a channel). You must tag such queries by passing true to this method. This also applies when consuming other queries, for example:
func Exclamate(q Query[string]) Query[string] { result := NewQuery(func() Enumerator[string] { next := q.Enumerator() return func() (string, bool) { if t, ok := next(); ok { return t + "!", true } return "", false } }) result.SetOneShot(q.OneShotOption()) }
Note that a non one-shot query doesn't guarantee that it won't consume its inputs. It only says that this query can be enumerated multiple times. For example, q.Memoize() is never one-shot, even though it may consume a one-shot q.
The Pipe convenience function offers a simpler mechanism to implement Queries and will automatically tag the output query as one-shot if the input query is. Prefer it over NewQuery when it makes sense.
Source Files ¶
- Cast.go
- Memoize.go
- OfType.go
- Pipe.go
- Reader.go
- aggregate.go
- append.go
- array.go
- buffer.go
- channel.go
- chunk.go
- concat.go
- contains.go
- count.go
- default.go
- distinct.go
- element.go
- enumerator.go
- error.go
- every.go
- except.go
- first.go
- flatten.go
- get.go
- groupby.go
- groupjoin.go
- index.go
- intersect.go
- iota.go
- join.go
- keyvalue.go
- length.go
- lookup.go
- map.go
- math.go
- maybe.go
- minmax.go
- none.go
- orderby.go
- package.go
- pairwise.go
- powerset.go
- predicates.go
- prepend.go
- query.go
- repeat.go
- reverse.go
- sample.go
- scanner.go
- select.go
- sequence.go
- set.go
- single.go
- skip.go
- slice.go
- slide.go
- string.go
- take.go
- union.go
- util.go
- value.go
- where.go
- zip.go