0

Consider

   val myseq = Array(1,2,3,4,5)
   val mysum = myseq.foldLeft(0){_ + _}

Is there not a defined aggregator for sum(), count(), etc? Along the lines of:

   import math.SomeLibraryClass._

   val myseq = Array(1,2,3,4,5)
   val mysum = myseq.foldLeft(0.0)(sum) 

Or for the case of groups of (row-based) sums:

   val rowSums = rows.map {sum}

(where by default the initial value is 0)

Update

So from the comments it appears there is no static (scala object-based) method for this and the correct syntax is:

   val rowSums = rows.map {_.sum}

Here it is:

scala> val arr = Array(Array(1,2,3), Array(4,5,6))
arr: Array[Array[Int]] = Array(Array(1, 2, 3), Array(4, 5, 6))

scala> arr.map(_.sum)
res23: Array[Int] = Array(6, 15)
3
  • Like Array(1,2,3,4,5).sum Commented Jan 27, 2015 at 21:59
  • @m-z yes, that .. I am looking now to see where that "lives" in the library. OK in TraversableOnce - which is where we would expect .. so must be my usage is not optimal. Commented Jan 27, 2015 at 22:00
  • @javadba scala-lang.org/api/current/… Commented Jan 27, 2015 at 22:02

1 Answer 1

1

As stated in my comment, there's already a sum method defined on collections, though it requires an implicit Numeric[A] for some M[A].

Perhaps you may be interested in the methods contained in the Numeric trait. For example, sum is defined in TraversableOnce like this:

def sum[B >: A](implicit num: Numeric[B]): B = foldLeft(num.zero)(num.plus)

So in a sense, Scala does have some static references to methods like sum. There are quite a few instances of Numeric in the standard library, for each numeric type. (seen here)

For instance, there is IntIsIntegral, which a Numeric[Int]. You could use it explicitly like this:

Array(1, 2, 3, 4, 5).fold(Numeric.IntIsIntegral.zero)(Numeric.IntIsIntegral.plus)

But why would you want to? The thing is, this will only work for Int, when requiring an implicit Numeric[A] will work for any numeric type that has such an implicit defined.

This breaks, since the types are different:

scala> Array(1.0, 2.0, 3.0, 4.0, 5.0).fold(Numeric.IntIsIntegral.zero)(Numeric.IntIsIntegral.plus)
<console>:8: error: type mismatch;
 found   : (Int, Int) => Int
 required: (AnyVal, AnyVal) => AnyVal
              Array(1.0,2.0,3.0,4.0,5.0).fold(Numeric.IntIsIntegral.zero)(Numeric.IntIsIntegral.plus)

So, technically yes, functions like that exist. But using Numeric in this case is better.

Sign up to request clarification or add additional context in comments.

2 Comments

After reading your answer, it still seems that the correct usage is as shown in my update: i.e. an instance-based _.sum as opposed to object based sum. If I have interpreted your answer incorrectly pls elaborate ;) Anyways am upvoting.
@javadba I'm not saying that using the static objects is correct--I'm just stating that such things do exist. Using Array(..).sum and matrix.map(_.sum) is certainly better. i.e. taking advantage of things that are in the standard collections library. However, if you need to implement some custom generic numeric aggregation, then the Numeric trait is definitely something to check out.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.