Skip to content

Navigation Menu

Sign in
Appearance settings

Search code, repositories, users, issues, pull requests...

Provide feedback

We read every piece of feedback, and take your input very seriously.

Saved searches

Use saved searches to filter your results more quickly

Appearance settings
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
12 changes: 11 additions & 1 deletion 12 core/src/main/scala/cats/UnorderedFoldable.scala
Original file line number Diff line number Diff line change
Expand Up @@ -21,7 +21,7 @@

package cats

import cats.kernel.CommutativeMonoid
import cats.kernel.{CommutativeMonoid, CommutativeSemigroup}
import scala.collection.immutable.{Queue, Seq, SortedMap, SortedSet}
import scala.util.Try

Expand All @@ -35,6 +35,16 @@ trait UnorderedFoldable[F[_]] extends Serializable {
def unorderedFold[A: CommutativeMonoid](fa: F[A]): A =
unorderedFoldMap(fa)(identity)

/**
* Reduce this unordered structure by combining its elements with a [[CommutativeSemigroup]] instance.
*
* If there are no elements, the result is `None`.
*/
def unorderedReduceOption[A: CommutativeSemigroup](fa: F[A]): Option[A] = {
val reducer = CommutativeMonoid[Option[A]]
unorderedFoldMap(fa)(a => Some(a): Option[A])(using reducer)
}

/**
* Fold in a [[CommutativeApplicative]] context by mapping the `A` values to `G[B]`. combining
* the `B` values using the given `CommutativeMonoid[B]` instance.
Expand Down
5 changes: 5 additions & 0 deletions 5 core/src/main/scala/cats/syntax/unorderedFoldable.scala
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,8 @@
package cats
package syntax

import cats.kernel.CommutativeSemigroup

trait UnorderedFoldableSyntax extends UnorderedFoldable.ToUnorderedFoldableOps {
implicit final def catsSyntaxUnorderedFoldableOps[F[_]: UnorderedFoldable, A](fa: F[A]): UnorderedFoldableOps[F, A] =
new UnorderedFoldableOps[F, A](fa)
Expand Down Expand Up @@ -66,4 +68,7 @@ final class UnorderedFoldableOps[F[_], A](private val fa: F[A]) extends AnyVal {
*/
def count(p: A => Boolean)(implicit F: UnorderedFoldable[F]): Long =
F.count(fa)(p)

def unorderedReduceOption(implicit A: CommutativeSemigroup[A], F: UnorderedFoldable[F]): Option[A] =
F.unorderedReduceOption(fa)
}
3 changes: 3 additions & 0 deletions 3 laws/src/main/scala/cats/laws/UnorderedFoldableLaws.scala
Original file line number Diff line number Diff line change
Expand Up @@ -33,6 +33,9 @@ trait UnorderedFoldableLaws[F[_]] {
def unorderedFoldMapAIdentity[A, B: CommutativeMonoid](fa: F[A], f: A => B): IsEq[B] =
F.unorderedFoldMapA[Id, A, B](fa)(f) <-> F.unorderedFoldMap(fa)(f)

def unorderedReduceOptionConsistentWithUnorderedFold[A: CommutativeMonoid](fa: F[A]): IsEq[Option[A]] =
F.unorderedReduceOption(fa) <-> (if (F.isEmpty(fa)) None else Some(F.unorderedFold(fa)))

def forallConsistentWithExists[A](fa: F[A], p: A => Boolean): Boolean =
if (F.forall(fa)(p)) {
val negationExists = F.exists(fa)(a => !p(a))
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -28,6 +28,7 @@ import Prop.*
import org.typelevel.discipline.Laws
import cats.kernel.CommutativeMonoid
import cats.instances.boolean.*
import cats.instances.option.*

trait UnorderedFoldableTests[F[_]] extends Laws {
def laws: UnorderedFoldableLaws[F]
Expand All @@ -53,7 +54,10 @@ trait UnorderedFoldableTests[F[_]] extends Laws {
"forall is lazy" -> forAll(laws.forallLazy[A] _),
"contains consistent with exists" -> forAll(laws.containsConsistentWithExists[A] _),
"contains consistent with forall" -> forAll(laws.containsConsistentWithForall[A] _),
"contains all elements from itself" -> forAll(laws.containsAllElementsFromItself[A] _)
"contains all elements from itself" -> forAll(laws.containsAllElementsFromItself[A] _),
"unorderedReduceOption consistent with unorderedFold" -> forAll(
laws.unorderedReduceOptionConsistentWithUnorderedFold[A] _
)
)
}

Expand Down
Loading
Morty Proxy This is a proxified and sanitized view of the page, visit original site.