Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

How to sum up based on a Tuples first elem?

Tags:

tuples

scala

I have a 3-tuple list like the following [I added line breaks for readability]:

(2, 127, 3)
(12156, 127, 3)
(4409, 127, 2) <-- 4409 occurs 2x
(1312, 127, 12) <-- 1312 occurs 3x

(4409, 128, 1) <-- 
(12864, 128, 1)
(1312, 128, 1) <-- 
(2664, 128, 2)

(12865, 129, 1)
(183, 129, 1)
(12866, 129, 2)
(1312, 129, 10) <--

I want to sum up based on the first entry. The first entry should be unique.

The result should look like this:

(2, 127, 3)
(12156, 127, 3)
(4409, 127, 3) <- new sum = 3
(1312, 127, 23) <- new sum = 23

(12864, 128, 1)
(2664, 128, 2)

(12865, 129, 1)
(183, 129, 1)
(12866, 129, 2)

How can I achieve this in Scala?

like image 777
user1243091 Avatar asked Apr 08 '12 19:04

user1243091


People also ask

How do you reference the first element of a tuple?

Use indexing to get the first element of each tuple Use a for-loop to iterate through a list of tuples. Within the for-loop, use the indexing tuple[0] to access the first element of each tuple, and append it.

How do you sum tuple values?

How to find a sum of a tuple in Python. To find a sum of the tuple in Python, use the sum() method. Define a tuple with number values and pass the tuple as a parameter to the sum() function; in return, you will get the sum of tuple items.

How do you sum a tuple element in Python?

Using sum() to get the total in a tuple The built-in sum() function in Python is used to return the sum of an iterable. To get the sum total of a tuple of numbers, you can pass the tuple as an argument to the sum() function.

Can sum be used in tuple?

A list of tuple basically contains tuples enclosed in a list. The map function applies a given function/operation to every item in an iterable (such as list, tuple). It returns a list as the result. The 'sum' method can be used to add the elements in an iterable.


2 Answers

Try this:

list groupBy {_._1} mapValues {v => (v.head._1, v.head._2, v map {_._3} sum)}

The middle entry is preserved and it always takes the first one that appeared in the input list.

like image 154
Tomasz Nurkiewicz Avatar answered Oct 29 '22 02:10

Tomasz Nurkiewicz


If you can just ignore the middle entry, then:

val l = List(('a,'e,1), ('b,'f,2), ('a,'g,3), ('b,'h,4))
l.groupBy(_._1).mapValues(_.map(_._3).sum) 
// Map('b -> 6, 'a -> 4)

If you have to keep the middle entry around:

l.groupBy(_._1).map { 
  case (_, values) =>
    val (a,b,_) = values.head
    (a, b, values.map(_._3).sum)
} 
// List(('b,'f,6), ('a,'e,4))
like image 37
dhg Avatar answered Oct 29 '22 01:10

dhg