Last active
February 22, 2024 09:42
-
-
Save davidandrzej/5006950 to your computer and use it in GitHub Desktop.
Scala Map.mapValues returns a (lazy) view. Hilarity ensues.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
// | |
// TIL Scala Map.mapValues returns a lazy view | |
// | |
// This has the horrific consequence that supplying a non-pure function | |
// can yield a result map with unexpected / undesired behavior (see below) | |
// | |
// Further discussion here: | |
// http://stackoverflow.com/questions/14882642/scala-why-mapvalues-produces-a-view-and-is-there-any-stable-alternatives | |
// https://issues.scala-lang.org/browse/SI-4776 | |
// | |
object TrickyMapValues extends App { | |
// Here comes trouble | |
var sideFX = 0.0 | |
def nonPure(x: Double) = { | |
sideFX += 1.0 | |
x + sideFX | |
} | |
val myMap = Map("a" -> 1.0, "b" -> 2.0) | |
val mapValues = myMap.mapValues(nonPure) | |
// If you think these should produce identical values, | |
// prepare to be delightfully surprised | |
println("sum1 = %.2f".format(mapValues.values.sum)) | |
println("sum2 = %.2f".format(mapValues.values.sum)) | |
println("sum3 = %.2f".format(mapValues.values.sum)) | |
} |
mapValues
is now deprected an replaced by view.mapValues
(which is explicitely lazy).
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Ran across your blog and tried this out. So tricky! I have never used mapValues but probably won't for sure now.