views:

305

answers:

3

This is more a question of style and preference but here goes: when should I use scala.Array? I use List all the time and occasionally run into Seq, Map and the like, but I've never used nor seen Array in the wild. Is it just there for Java compatibility? Am I missing a common use-case?

+3  A: 

An array is appropriate when you have a number of items of the same (or compatible) class, and you know in advance the exact count of those items, or a reasonable upper bound, and you're interested in fast random access and perhaps in-place alteration of items, but after setting it up, you will never ever insert or remove items from somewhere in the list.

Or stated in another way, it's an aggregate data structure with less bells and whistles than the Collection types, with slightly less overhead and slightly better performance depending on how it's used.

A very contrived example: You're in the business of producing functions, and quality testing for these functions involves checking their performance or results for a set of 1000 fixed input values. Moreover, you decide not to keep these values in a file, but rather you hard code them into your program. An array would be appropriate.

Carl Smotricz
+2  A: 

Interfacing with Java APIs is one case. Also unlike Java arrays scala arrays are invariant and hence doesn't have any advantage over lists because of that.

Hemant Kumar
+7  A: 

First of all, let's make a disclaimer here. Scala 2.7's Array tries to be an Java Array and a Scala Collection at the same time. It mostly succeeds, but fail at both for some corner cases. Unfortunately, these corner cases can happen to good people with normal code, so Scala 2.8 is departing from that.

On Scala 2.8, there's Array, which is Java Array. That means it is a contiguous memory space, which stores either references or primitives (and, therefore, may have different element sizes), and can be randomly accessed pretty fast. It also has lousy methods, an horrible toString implementation, and performs badly when using generics and primitives at the same time (eg: def f[T](a: Array[T]) = ...; f(Array(1,2,3))).

And, then, there is GenericArray, which is a Scala Collection backed by an Array. It always stores boxed primitives, so it doesn't have the performance problems when mixing primitives and generics but, on the other hand, it doesn't have the performance gains of a purely primitive (non-generic) primitive array.

So, when to use what? An Array has the following characteristics:

  • O(1) random read and write
  • O(n) append/prepend/insert/delete
  • mutable

If you don't need generics, or your generics can be stated as [T <: AnyRef], thus excluding primitives, which are AnyVal, and those characteristics are optimal for your code, then go for it.

If you do need generics, including primitives, and those characteristics are optimal for your code, use GenericArray on Scala 2.8. Also, if you want a true Collection, with all of its methods, you may want to use it as well, instead of depending on implicit conversions.

If you want immutability or if you need good performance for append, prepend, insert or delete, look for some other collection.

Daniel
Thanks, Daniel, this is a great answer.
pr1001