Skip to content

Commit 4a70ff1

Browse files
authored
Merge pull request #19 from joshlemer/multiset-multidict-tostring
Fix MultiSet#toString and MultiDict#toString
2 parents 1a46759 + 386b60d commit 4a70ff1

File tree

4 files changed

+92
-1
lines changed

4 files changed

+92
-1
lines changed

src/main/scala/scala/collection/MultiDict.scala

+4
Original file line numberDiff line numberDiff line change
@@ -13,6 +13,8 @@ trait MultiDict[K, V]
1313
with MultiDictOps[K, V, MultiDict, MultiDict[K, V]]
1414
with Equals {
1515

16+
override protected[this] def className: String = "MultiDict"
17+
1618
def multiDictFactory: MapFactory[MultiDict] = MultiDict
1719
override protected def fromSpecific(coll: IterableOnce[(K, V)]): MultiDict[K, V] = multiDictFactory.from(coll)
1820
override protected def newSpecificBuilder: mutable.Builder[(K, V), MultiDict[K, V]] = multiDictFactory.newBuilder
@@ -196,6 +198,8 @@ trait MultiDictOps[K, V, +CC[X, Y] <: MultiDict[X, Y], +C <: MultiDict[K, V]]
196198
def filterSets(p: ((K, Set[V])) => Boolean): C =
197199
fromSpecificSets(new View.Filter(sets, p, isFlipped = false))
198200

201+
override def addString(sb: StringBuilder, start: String, sep: String, end: String): StringBuilder =
202+
iterator.map { case (k, v) => s"$k -> $v" }.addString(sb, start, sep, end)
199203
}
200204

201205
object MultiDictOps {

src/main/scala/scala/collection/MultiSet.scala

+2
Original file line numberDiff line numberDiff line change
@@ -12,6 +12,8 @@ trait MultiSet[A]
1212
with MultiSetOps[A, MultiSet, MultiSet[A]]
1313
with Equals {
1414

15+
override protected[this] def className: String = "MultiSet"
16+
1517
override def iterableFactory: IterableFactory[MultiSet] = MultiSet
1618
override protected def fromSpecific(coll: IterableOnce[A]): MultiSet[A] = iterableFactory.from(coll)
1719
override protected def newSpecificBuilder: mutable.Builder[A, MultiSet[A]] = iterableFactory.newBuilder

src/test/scala/scala/collection/MultiMapTest.scala renamed to src/test/scala/scala/collection/MultiDictTest.scala

+47-1
Original file line numberDiff line numberDiff line change
@@ -6,7 +6,7 @@ import scala.collection.immutable.List
66
import org.junit.{Assert, Test}
77

88
@RunWith(classOf[JUnit4])
9-
class MultiMapTest {
9+
class MultiDictTest {
1010

1111
@Test
1212
def equality(): Unit = {
@@ -72,5 +72,51 @@ class MultiMapTest {
7272
val filteredT: MultiDict[String, Int] = filtered
7373
Assert.assertEquals(Seq.empty, filtered.toSeq)
7474
}
75+
@Test
76+
def testToString(): Unit = {
77+
78+
val prefix = "MultiDict("
79+
val suffix = ")"
80+
81+
def run(ms: MultiDict[Int, Int]): Unit = {
82+
val actual = ms.toString
83+
assert(actual.startsWith(prefix), s"`$actual` does not start with `$prefix`")
84+
assert(actual.endsWith(suffix), s"`$actual` does not end with `$suffix`")
85+
86+
// The order of elements in the multiset are not defined, so this test should be robust to order changes
87+
88+
val expected =
89+
actual
90+
.stripPrefix(prefix)
91+
.stripSuffix(suffix)
92+
.split(",")
93+
.iterator
94+
.flatMap { s =>
95+
if (s.isEmpty) None
96+
else {
97+
val Array(keyString, valueString) = s.split("->")
98+
Some(keyString.trim.toInt -> valueString.trim.toInt)
99+
}
100+
}
101+
.to(MultiDict)
102+
Assert.assertEquals(ms, expected)
103+
}
104+
105+
def runForFactory(factory: MapFactory[MultiDict]): Unit = {
106+
Assert.assertEquals(factory().toString, s"$prefix$suffix")
107+
Assert.assertEquals(factory(1 -> 1).toString, s"${prefix}1 -> 1${suffix}")
108+
109+
run(factory())
110+
run(factory(1 -> 1))
111+
run(factory(1234 -> 2))
112+
run(factory(1 -> 5,2 -> 6,3 -> 7))
113+
run(factory(1 -> 1,1 -> 2,1 -> 3,2 -> 1,3 -> 3))
114+
run(factory(1 -> 1,1 -> 2,1 -> 3,2 -> 4,2 -> 5,2 -> 6,2 -> 7,3 -> 8))
115+
}
116+
117+
runForFactory(MultiDict)
118+
runForFactory(mutable.MultiDict)
119+
runForFactory(immutable.MultiDict)
120+
}
75121

76122
}

src/test/scala/scala/collection/MultiSetTest.scala

+39
Original file line numberDiff line numberDiff line change
@@ -46,4 +46,43 @@ class MultiSetTest {
4646
)
4747
}
4848

49+
@Test
50+
def testToString(): Unit = {
51+
52+
def run(ms: MultiSet[Int]): Unit = {
53+
val actual = ms.toString
54+
assert(actual.startsWith("MultiSet("), s"`$actual` does not start with `MultiSet(`")
55+
assert(actual.endsWith(")"), s"`$actual` does not end with `)`")
56+
57+
// The order of elements in the multiset are not defined, so this test should be robust to order changes
58+
Assert.assertEquals(ms,
59+
actual
60+
.stripPrefix("MultiSet(")
61+
.stripSuffix(")")
62+
.split(",")
63+
.iterator
64+
.flatMap (_.trim match {
65+
case "" => None
66+
case s => Some(s.toInt)
67+
})
68+
.to(MultiSet))
69+
}
70+
71+
def runForFactory(factory: IterableFactory[MultiSet]): Unit = {
72+
Assert.assertEquals(factory().toString, "MultiSet()")
73+
Assert.assertEquals(factory(1).toString, "MultiSet(1)")
74+
75+
run(factory())
76+
run(factory(1))
77+
run(factory(1234))
78+
run(factory(1,2,3))
79+
run(factory(1,1,1,2,3))
80+
run(factory(1,1,1,2,2,2,2,3))
81+
}
82+
83+
runForFactory(MultiSet)
84+
runForFactory(mutable.MultiSet)
85+
runForFactory(immutable.MultiSet)
86+
}
87+
4988
}

0 commit comments

Comments
 (0)