Skip to content
This repository has been archived by the owner on Dec 22, 2021. It is now read-only.

Commit

Permalink
Rename TupleNZipped to LazyZipN
Browse files Browse the repository at this point in the history
  • Loading branch information
marcelocenerine committed Oct 27, 2017
1 parent c7d7600 commit 83b2836
Show file tree
Hide file tree
Showing 2 changed files with 67 additions and 68 deletions.
69 changes: 34 additions & 35 deletions collections/src/main/scala/strawman/collection/LazyZipOps.scala
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,7 @@ import scala.language.implicitConversions
final class LazyZipOps[A, C1 <: Iterable[A]] private[collection](`this`: C1) {

/** Analogous to `zip` except that the elements in each collection are not consumed until a strict operation is
* invoked on the returned `Tuple2Zipped` decorator.
* invoked on the returned `LazyZip2` decorator.
*
* Calls to `lazyZip` can be chained to support higher arities (up to 4) without incurring the expense of
* constructing and deconstructing intermediary tuples.
Expand All @@ -17,26 +17,26 @@ final class LazyZipOps[A, C1 <: Iterable[A]] private[collection](`this`: C1) {
* // res == List(4, 8, 12)
* }}}
*
* @param that the iterable providing the second half of each eventual pair
* @tparam B the type of the element in the second half of each eventual pair
* @return a decorator `Tuple2Zipped` that allows strict operations to be performed on the lazily evaluated pairs
* @param that the iterable providing the second element of each eventual pair
* @tparam B the type of the second element in each eventual pair
* @return a decorator `LazyZip2` that allows strict operations to be performed on the lazily evaluated pairs
* or chained calls to `lazyZip`. Implicit conversion to `Iterable[(A, B)]` is also supported.
*/
def lazyZip[B](that: Iterable[B]): Tuple2Zipped[A, B, C1] = new Tuple2Zipped(`this`, that)
def lazyZip[B](that: Iterable[B]): LazyZip2[A, B, C1] = new LazyZip2(`this`, that)
}

/** Decorator representing lazily zipped tuples of arity 2. */
final class Tuple2Zipped[El1, El2, C1 <: Iterable[El1]] private[collection](coll1: C1, coll2: Iterable[El2]) {
/** Decorator representing lazily zipped pairs. */
final class LazyZip2[El1, El2, C1 <: Iterable[El1]] private[collection](coll1: C1, coll2: Iterable[El2]) {

/** Zips `that` iterable collection with an already lazily zipped `Tuple2Zipped`. The elements in each collection are
* not consumed until a strict operation is invoked on the returned `Tuple3Zipped` decorator.
/** Zips `that` iterable collection with an existing `LazyZip2`. The elements in each collection are
* not consumed until a strict operation is invoked on the returned `LazyZip3` decorator.
*
* @param that the iterable providing the third element of each eventual tuple
* @tparam B the type of the third element in each eventual tuple
* @return a decorator `Tuple3Zipped` that allows strict operations to be performed on the lazily evaluated tuples or
* @param that the iterable providing the third element of each eventual triple
* @tparam B the type of the third element in each eventual triple
* @return a decorator `LazyZip3` that allows strict operations to be performed on the lazily evaluated tuples or
* chained calls to `lazyZip`. Implicit conversion to `Iterable[(El1, El2, B)]` is also supported.
*/
def lazyZip[B](that: Iterable[B]): Tuple3Zipped[El1, El2, B, C1] = new Tuple3Zipped(coll1, coll2, that)
def lazyZip[B](that: Iterable[B]): LazyZip3[El1, El2, B, C1] = new LazyZip3(coll1, coll2, that)

def map[B, C](f: (El1, El2) => B)(implicit bf: BuildFrom[C1, B, C]): C = {
bf.fromSpecificIterable(coll1)(new View[B] {
Expand Down Expand Up @@ -121,26 +121,26 @@ final class Tuple2Zipped[El1, El2, C1 <: Iterable[El1]] private[collection](coll
override def toString = s"$coll1.lazyZip($coll2)"
}

object Tuple2Zipped {
implicit def tuple2ZippedToIterable[El1, El2](zipped2: Tuple2Zipped[El1, El2, _]): View[(El1, El2)] =
object LazyZip2 {
implicit def lazyZip2ToIterable[El1, El2](zipped2: LazyZip2[El1, El2, _]): View[(El1, El2)] =
new View[(El1, El2)] { def iterator() = zipped2.iterator() }
}


/** Decorator representing lazily zipped tuples of arity 3. */
final class Tuple3Zipped[El1, El2, El3, C1 <: Iterable[El1]] private[collection](coll1: C1,
coll2: Iterable[El2],
coll3: Iterable[El3]) {
/** Decorator representing lazily zipped triples. */
final class LazyZip3[El1, El2, El3, C1 <: Iterable[El1]] private[collection](coll1: C1,
coll2: Iterable[El2],
coll3: Iterable[El3]) {

/** Zips `that` iterable collection with an already lazily zipped `Tuple3Zipped`. The elements in each collection are
* not consumed until a strict operation is invoked on the returned `Tuple4Zipped` decorator.
/** Zips `that` iterable collection with an existing `LazyZip3`. The elements in each collection are
* not consumed until a strict operation is invoked on the returned `LazyZip4` decorator.
*
* @param that the iterable providing the fourth element of each eventual tuple
* @tparam B the type of the fourth element in each eventual tuple
* @return a decorator `Tuple4Zipped` that allows strict operations to be performed on the lazily evaluated tuples.
* @param that the iterable providing the fourth element of each eventual 4-tuple
* @tparam B the type of the fourth element in each eventual 4-tuple
* @return a decorator `LazyZip4` that allows strict operations to be performed on the lazily evaluated tuples.
* Implicit conversion to `Iterable[(El1, El2, El3, B)]` is also supported.
*/
def lazyZip[B](that: Iterable[B]): Tuple4Zipped[El1, El2, El3, B, C1] = new Tuple4Zipped(coll1, coll2, coll3, that)
def lazyZip[B](that: Iterable[B]): LazyZip4[El1, El2, El3, B, C1] = new LazyZip4(coll1, coll2, coll3, that)

def map[B, C](f: (El1, El2, El3) => B)(implicit bf: BuildFrom[C1, B, C]): C = {
bf.fromSpecificIterable(coll1)(new View[B] {
Expand Down Expand Up @@ -234,18 +234,18 @@ final class Tuple3Zipped[El1, El2, El3, C1 <: Iterable[El1]] private[collection]
override def toString = s"$coll1.lazyZip($coll2).lazyZip($coll3)"
}

object Tuple3Zipped {
implicit def tuple3ZippedToIterable[El1, El2, El3](zipped3: Tuple3Zipped[El1, El2, El3, _]): View[(El1, El2, El3)] =
object LazyZip3 {
implicit def lazyZip3ToIterable[El1, El2, El3](zipped3: LazyZip3[El1, El2, El3, _]): View[(El1, El2, El3)] =
new View[(El1, El2, El3)] { def iterator() = zipped3.iterator() }
}



/** Decorator representing lazily zipped tuples of arity 4. */
final class Tuple4Zipped[El1, El2, El3, El4, C1 <: Iterable[El1]] private[collection](coll1: C1,
coll2: Iterable[El2],
coll3: Iterable[El3],
coll4: Iterable[El4]) {
/** Decorator representing lazily zipped 4-tuples. */
final class LazyZip4[El1, El2, El3, El4, C1 <: Iterable[El1]] private[collection](coll1: C1,
coll2: Iterable[El2],
coll3: Iterable[El3],
coll4: Iterable[El4]) {

def map[B, C](f: (El1, El2, El3, El4) => B)(implicit bf: BuildFrom[C1, B, C]): C = {
bf.fromSpecificIterable(coll1)(new View[B] {
Expand Down Expand Up @@ -346,8 +346,7 @@ final class Tuple4Zipped[El1, El2, El3, El4, C1 <: Iterable[El1]] private[collec
override def toString = s"$coll1.lazyZip($coll2).lazyZip($coll3).lazyZip($coll4)"
}

object Tuple4Zipped {
implicit def tuple4ZippedToIterable[El1, El2, El3, El4](zipped4: Tuple4Zipped[El1, El2, El3, El4, _]
): View[(El1, El2, El3, El4)] =
object LazyZip4 {
implicit def lazyZip4ToIterable[El1, El2, El3, El4](zipped4: LazyZip4[El1, El2, El3, El4, _]): View[(El1, El2, El3, El4)] =
new View[(El1, El2, El3, El4)] { def iterator() = zipped4.iterator() }
}
66 changes: 33 additions & 33 deletions test/junit/src/test/scala/strawman/collection/LazyZipOpsTest.scala
Original file line number Diff line number Diff line change
Expand Up @@ -22,68 +22,68 @@ class LazyZipOpsTest {
private val sortedSet = TreeSet(1, 2, 3)

@Test
def tuple2Zipped_map(): Unit = {
def lazyZip2_map(): Unit = {
val res: List[(Int, Int)] = zipped2.map((a, b) => (a, b))

assertEquals(List((1, 1), (2, 2), (3, 3)), res)
}

@Test
def tuple2Zipped_flatMap(): Unit = {
def lazyZip2_flatMap(): Unit = {
val res: List[(Int, Int)] = zipped2.flatMap((a, b) => List((a, b)))

assertEquals(List((1, 1), (2, 2), (3, 3)), res)
}

@Test
def tuple2Zipped_filter(): Unit = {
def lazyZip2_filter(): Unit = {
val res: List[(Int, Int)] = zipped2.filter((a, _) => a % 2 == 0)

assertEquals(List((2, 2)), res)
}

@Test
def tuple2Zipped_exists(): Unit = {
def lazyZip2_exists(): Unit = {
assertTrue(zipped2.exists((a, b) => a + b > 5))
assertFalse(zipped2.exists((a, b) => a + b < 0))
}

@Test
def tuple2Zipped_forall(): Unit = {
def lazyZip2_forall(): Unit = {
assertTrue(zipped2.forall((a, b) => a + b > 0))
assertFalse(zipped2.forall((a, b) => a + b > 2))
}

@Test
def tuple2Zipped_foreach(): Unit = {
def lazyZip2_foreach(): Unit = {
var res = ""
zipped2.foreach((a, b) => res += s"[$a,$b]")

assertEquals("[1,1][2,2][3,3]", res)
}

@Test
def tuple2Zipped_toIterable(): Unit = {
def lazyZip2_toIterable(): Unit = {
val iter: Iterable[(Int, Int)] = zipped2

assertEquals(List((1, 1), (2, 2), (3, 3)), iter.to(List))
}

@Test
def tuple2Zipped_empty(): Unit = {
def lazyZip2_empty(): Unit = {
assertTrue(Nil.lazyZip(xs).isEmpty)
assertTrue(xs.lazyZip(Nil).isEmpty)
}

@Test
def tuple2Zipped_withOrdering(): Unit = {
def lazyZip2_withOrdering(): Unit = {
val res: TreeSet[Int] = sortedSet.lazyZip(ws).map(_ + _)

assertEquals(TreeSet(2, 4, 6), res)
}

@Test
def tuple2Zipped_withMap(): Unit = {
def lazyZip2_withMap(): Unit = {
val res: Map[Int, (String, String)] = map.lazyZip(ys).map { case ((k, v), s) => k -> (s, v) }

assertThat(res, either(
Expand All @@ -93,75 +93,75 @@ class LazyZipOpsTest {
}

@Test
def tuple2Zipped_withSortedMap(): Unit = {
def lazyZip2_withSortedMap(): Unit = {
val res: TreeMap[Int, (String, String)] = sortedMap.lazyZip(ys).map { case ((k, v), s) => k -> (s, v) }

assertEquals(Map(1 -> ("a", "foo"), 2 -> ("b", "bar")), res)
}

@Test
def tuple3Zipped_map(): Unit = {
def lazyZip3_map(): Unit = {
val res: List[(Int, Int, String)] = zipped3.map((a, b, c) => (a, b, c))

assertEquals(List((1, 1, "a"), (2, 2, "b"), (3, 3, "c")), res)
}

@Test
def tuple3Zipped_flatMap(): Unit = {
def lazyZip3_flatMap(): Unit = {
val res: List[(Int, Int, String)] = zipped3.flatMap((a, b, c) => List((a, b, c)))

assertEquals(List((1, 1, "a"), (2, 2, "b"), (3, 3, "c")), res)
}

@Test
def tuple3Zipped_filter(): Unit = {
def lazyZip3_filter(): Unit = {
val res: List[(Int, Int, String)] = zipped3.filter((a, _, _) => a % 2 != 0)

assertEquals(List((1, 1, "a"), (3, 3, "c")), res)
}

@Test
def tuple3Zipped_exists(): Unit = {
def lazyZip3_exists(): Unit = {
assertTrue(zipped3.exists((a, b, _) => a + b > 5))
assertFalse(zipped3.exists((a, b, _) => a + b < 0))
}

@Test
def tuple3Zipped_forall(): Unit = {
def lazyZip3_forall(): Unit = {
assertTrue(zipped3.forall((a, b, _) => (a + b) % 2 == 0))
assertFalse(zipped3.forall((a, b, _) => a + b > 5))
}

@Test
def tuple3Zipped_foreach(): Unit = {
def lazyZip3_foreach(): Unit = {
var res = ""
zipped3.foreach((a, b, c) => res += s"[$a,$b,$c]")

assertEquals("[1,1,a][2,2,b][3,3,c]", res)
}

@Test
def tuple3Zipped_toIterable(): Unit = {
def lazyZip3_toIterable(): Unit = {
val iter: Iterable[(Int, Int, String)] = zipped3

assertEquals(List((1, 1, "a"), (2, 2, "b"), (3, 3, "c")), iter.to(List))
}

@Test
def tuple3Zipped_empty(): Unit = {
def lazyZip3_empty(): Unit = {
assertTrue(zipped2.lazyZip(Nil).isEmpty)
assertTrue(Nil.lazyZip(Nil).lazyZip(xs).isEmpty)
}

@Test
def tuple3Zipped_withOrdering(): Unit = {
def lazyZip3_withOrdering(): Unit = {
val res: TreeSet[Int] = sortedSet.lazyZip(xs).lazyZip(ws).map(_ + _ + _)

assertEquals(TreeSet(3, 6, 9), res)
}

@Test
def tuple3Zipped_withMap(): Unit = {
def lazyZip3_withMap(): Unit = {
val res: Map[Int, (Int, String, String)] = map.lazyZip(ws).lazyZip(ys).map { case ((k, v), w, y) => k -> (w, y, v) }

assertThat(res, either(
Expand All @@ -171,76 +171,76 @@ class LazyZipOpsTest {
}

@Test
def tuple3Zipped_withSortedMap(): Unit = {
def lazyZip3_withSortedMap(): Unit = {
val res: TreeMap[Int, (Int, String, String)] = sortedMap.lazyZip(ws).lazyZip(ys)
.map { case ((k, v), w, y) => k -> (w, y, v) }

assertEquals(Map(1 -> (1, "a", "foo"), 2 -> (2, "b", "bar")), res)
}

@Test
def tuple4Zipped_map(): Unit = {
def lazyZip4_map(): Unit = {
val res: List[(Int, Int, String, Boolean)] = zipped4.map((a, b, c, d) => (a, b, c, d))

assertEquals(List((1, 1, "a", true), (2, 2, "b", false), (3, 3, "c", true)), res)
}

@Test
def tuple4Zipped_flatMap(): Unit = {
def lazyZip4_flatMap(): Unit = {
val res: List[(Int, Int, String, Boolean)] = zipped4.flatMap((a, b, c, d) => List((a, b, c, d)))

assertEquals(List((1, 1, "a", true), (2, 2, "b", false), (3, 3, "c", true)), res)
}

@Test
def tuple4Zipped_filter(): Unit = {
def lazyZip4_filter(): Unit = {
val res: List[(Int, Int, String, Boolean)] = zipped4.filter((_, _, _, d) => d)

assertEquals(List((1, 1, "a", true), (3, 3, "c", true)), res)
}

@Test
def tuple4Zipped_exists(): Unit = {
def lazyZip4_exists(): Unit = {
assertTrue(zipped4.exists((a, b, c, d) => a + b > 5 && !c.isEmpty && d))
assertFalse(zipped4.exists((a, b, c, d) => a + b > 5 && !c.isEmpty && !d))
}

@Test
def tuple4Zipped_forall(): Unit = {
def lazyZip4_forall(): Unit = {
assertTrue(zipped4.forall((a, b, _, _) => (a + b) % 2 == 0))
assertFalse(zipped4.forall((a, b, _, d) => a + b > 0 && d))
}

@Test
def tuple4Zipped_foreach(): Unit = {
def lazyZip4_foreach(): Unit = {
var res = ""
zipped4.foreach((a, b, c, d) => res += s"[$a,$b,$c,$d]")

assertEquals("[1,1,a,true][2,2,b,false][3,3,c,true]", res)
}

@Test
def tuple4Zipped_toIterable(): Unit = {
def lazyZip4_toIterable(): Unit = {
val iter: Iterable[(Int, Int, String, Boolean)] = zipped4

assertEquals(List((1, 1, "a", true), (2, 2, "b", false), (3, 3, "c", true)), iter.to(List))
}

@Test
def tuple4Zipped_empty(): Unit = {
def lazyZip4_empty(): Unit = {
assertTrue(zipped3.lazyZip(Nil).isEmpty)
assertTrue(Nil.lazyZip(Nil).lazyZip(Nil).lazyZip(xs).isEmpty)
}

@Test
def tuple4Zipped_withOrdering(): Unit = {
def lazyZip4_withOrdering(): Unit = {
val res: TreeSet[Int] = sortedSet.lazyZip(xs).lazyZip(ws).lazyZip(ws).map(_ + _ + _ + _)

assertEquals(TreeSet(4, 8, 12), res)
}

@Test
def tuple4Zipped_withMap(): Unit = {
def lazyZip4_withMap(): Unit = {
val res: Map[Int, (Int, Int, String, String)] = map.lazyZip(ws).lazyZip(xs).lazyZip(ys)
.map { case ((k, v), w, x, y) => k -> (w, x, y, v) }

Expand All @@ -251,7 +251,7 @@ class LazyZipOpsTest {
}

@Test
def tuple4Zipped_withSortedMap(): Unit = {
def lazyZip4_withSortedMap(): Unit = {
val res: TreeMap[Int, (Int, Int, String, String)] = sortedMap.lazyZip(ws).lazyZip(xs).lazyZip(ys)
.map { case ((k, v), w, x, y) => k -> (w, x, y, v) }

Expand Down

0 comments on commit 83b2836

Please sign in to comment.