How to get the possible pair combinaisons of values of a hashmap Scala - scala

I have a hashmap as follows :
val hm : HashMap[Int, List[String]] =
HashMap(
1 -> List("Eat", "Drink","Sleep", "work"),
2 -> List("Eat", "Sleep","Dance"),
3 -> List("Write", "Print","Dance")
)
I want to retrieve the possible pairs of this hashmap's values and return each pair separately in a list
I'm using the combinaisons function as
hm.mapValues(_.combinations(2).toList)
The result is :
Map(1-> List(List(Eat, Drink), List(Eat, Sleep), List(Eat, work), List(Drink, Sleep), List(Drink, work), List(Sleep, work)), 2-> List(List(Eat, Sleep), List(Eat, Dance), List(Sleep, Dance)), 3 -> List(List(Write, Print), List(Write, Dance), List(Print, Dance)))
yet the expected result should be three lists
List(List("Eat", "Drink","Sleep", "work"),List("Eat", "Sleep","Dance"))
List( List("Eat", "Drink","Sleep", "work"),List("Write", "Print","Dance"))
List(List("Eat", "Sleep","Dance"), List("Write", "Print","Dance"))
What am I missing

use only values of your map:
hm.values.toList.combinations(2).toList
https://scalafiddle.io/sf/ZGbHC4c/0

Related

Merge entries in Map without using loop in scala

Could someone suggest a best way to merge entries in map for below use case in scala (possibly without using loop)?
From
val map1 = Map(((1,"case0")->List(1,2,3)), ((2,"case0")->List(3,4,5)), ((1,"case1")->List(2,4,6)), ((2,"case1")->List(3)))
To
Map(((1,"nocase")->List(2)), ((2,"nocase")->List(3)))
You can do it as follows:
map1.groupBy(_._1._1).map{case (key, elements) => ((key, "nocase"), elements.values.reduce(_ intersect _ ))}
With the group you group the elements by the first element of the key, then with the map, you build the new key, with the "nocase" string as in your example. With elements.value you get all the elements for the given keys and you can reduce them with the intersect you get the expected output
Output:
Map[(Int, String),List[Int]] = Map((2,nocase) -> List(3), (1,nocase) -> List(2))

Map to List[Tuple2] in Scala - removes duplicates?

Am trying to convert a map to list of Tuples, given a map like below
Map("a"->2,"a"->4,"a"->5,"b"->6,"b"->1,"c"->3)
i want output like
List(("a",2),("a",4),("a",5),("b",6),("b",1),("c",3))
I tried following
val seq = inputMap.toList //output (a,5)(b,1)(c,3)
var list:List[(String,Int)] = Nil
for((k,v)<-inputMap){
(k,v) :: list
} //output (a,5)(b,1)(c,3)
Why does it remove duplicates? I dont see other tuples that has "a" as key.
That's because a Map doesn't allow duplicate keys:
val map = Map("a"->2,"a"->4,"a"->5,"b"->6,"b"->1,"c"->3)
println(map) // Map(a -> 5, b -> 1, c -> 3)
Since map has duplicate keys, it will remove duplicate entries while map creation itself.
Map("a"->2,"a"->4,"a"->5,"b"->6,"b"->1,"c"->3)
it will turn into,
Map(a -> 5, b -> 1, c -> 3)
so other operations will be performed on short map
The problem is with Map, whose keys are a Set, so you cannot have twice the same key. This is because Maps are dictionaries, which are made to access a value by its key, so keys MUST be unique. The builder thus keeps only the last value given with the key "a".
By the way, Map already has a method toList, that do exactly what you implemented.

Scala - map function - Only returned last element of a Map

I am new to Scala and trying out the map function on a Map.
Here is my Map:
scala> val map1 = Map ("abc" -> 1, "efg" -> 2, "hij" -> 3)
map1: scala.collection.immutable.Map[String,Int] =
Map(abc -> 1, efg -> 2, hij -> 3)
Here is a map function and the result:
scala> val result1 = map1.map(kv => (kv._1.toUpperCase, kv._2))
result1: scala.collection.immutable.Map[String,Int] =
Map(ABC -> 1, EFG -> 2, HIJ -> 3)
Here is another map function and the result:
scala> val result1 = map1.map(kv => (kv._1.length, kv._2))
result1: scala.collection.immutable.Map[Int,Int] = Map(3 -> 3)
The first map function returns all the members as expected however the second map function returns only the last member of the Map. Can someone explain why this is happening?
Thanks in advance!
In Scala, a Map cannot have duplicate keys. When you add a new key -> value pair to a Map, if that key already exists, you overwrite the previous value. If you're creating maps from functional operations on collections, then you're going to end up with the value corresponding to the last instance of each unique key. In the example you wrote, each string key of the original map map1 has the same length, and so all your string keys produce the same integer key 3 for result1. What's happening under the hood to calculate result1 is:
A new, empty map is created
You map "abc" -> 1 to 3 -> 3 and add it to the map. Result now contains 1 -> 3.
You map "efg" -> 2 to 3 -> 2 and add it to the map. Since the key is the same, you overwrite the existing value for key = 3. Result now contains 2 -> 3.
You map "hij" -> 3 to 3 -> 3 and add it to the map. Since the key is the same, you overwrite the existing value for key = 3. Result now contains 3 -> 3.
Return the result, which is Map(3 -> 3)`.
Note: I made a simplifying assumption that the order of the elements in the map iterator is the same as the order you wrote in the declaration. The order is determined by hash bin and will probably not match the order you added elements, so don't build anything that relies on this assumption.

How to find the number of (key , value) pairs in a map in scala?

I need to find the number of (key , value) pairs in a Map in my Scala code. I can iterate through the map and get an answer but I wanted to know if there is any direct function for this purpose or not.
you can use .size
scala> val m=Map("a"->1,"b"->2,"c"->3)
m: scala.collection.immutable.Map[String,Int] = Map(a -> 1, b -> 2, c -> 3)
scala> m.size
res3: Int = 3
Use Map#size:
The size of this traversable or iterator.
The size method is from TraversableOnce so, barring infinite sequences or sequences that shouldn't be iterated again, it can be used over a wide range - List, Map, Set, etc.

How to transpose a map with list values in Scala

How can this map of list,
Map (
"a" -> List(1, 2)
)
be transposed to this list of maps primarily using methods from the Scala libraries?
List(
Map("a" -> 1),
Map("a" -> 2)
)
I can code a solution myself but I am more interested in using library functionality so the preferred solution should use the Scala library where possible while remaining compact and moderately legible.
This second example illustrates the required transformation with a map with more than one entry.
From this,
Map (
10 -> List("10a", "10b", "10c"),
29 -> List("29a", "29b", "29c")
)
to this,
List(
Map(
10 -> "10a",
29 -> "29a"),
Map(
10 -> "10b",
29 -> "29b"),
Map(
10 -> "10c",
29 -> "29c")
)
It can be assumed that all values are lists of the same size.
Optionally the solution could handle the case where the values are empty lists but that is not required. If the solution supports empty list values then this input,
Map (
"a" -> List()
)
should result in List().
val m = Map (
10 -> List("10a", "10b", "10c"),
29 -> List("29a", "29b", "29c")
)
m.map{ case (k, vs) =>
vs.map(k -> _)
}.toList.transpose.map(_.toMap)
Note that this also handles your "empty list" case