Reputation: 240
*as we know that scala array contains data of the same type. But when I declared array as
var a = new Array[Any](3)
I am able to store different data types.
a(0)=5
a(1)="hello"
a(2)=1.5
how is it possible? if it is wrong then what is the option we have in scala to store different data types?*
Upvotes: 5
Views: 8943
Reputation: 14083
The notion of "same type" always depends on a level of generality. In Scala, the level of generality is determined by formal type.
Are 3 and 7 "of the same type"? If we write...
val a : Int = 3
val b : Int = 7
then they of of the same type Int
. But, if we define bit-length restricted Int
types (which we are very welcome to do in Scala), we might write
val a : Int2 = 3
val b : Int3 = 7
and they no longer appear to be of the same type!
If we define an inheritance hierarchy
trait Animal;
class Dog extends Animal;
class Frog extends Animal;
then do Dog
and Frog
have the same type? If we write
val d : Dog = new Dog
val f : Frog = new Frog
then it looks like the answer is no. But if we write
val d : Animal = new Dog
val f : Animal = new Frog
then they look like they do have the same type. Consistent with that, if I declare an array like
val arr : Array[Dog] = Array.ofDim[Dog](5)
then I can't put a frog in it, because a frog is not a dog. But if I declare the a similar array
val arr : Array[Animal] = Array.ofDim[Animal](5)
Then of course both frogs and dogs can go in it, because at the level of generality of Animal
, both Frogs and Dogs do have the same type.
In Scala Any
is a base type from which all other types derive. So, at a very high level of generality, 5
, "hello"
, and 1.5
, all have the same type Any
, just as at a high level of generality Frog
and Dog
have the same type Animal
. So there's no problem putting 5
, "hello"
, and 1.5
into an Array[Any]
.
Upvotes: 7
Reputation: 6548
Yes you are right about scala array
and you are indeed storing the data of same type
here. See this example:
scala> val a = Array(5,"hello",1.5)
a: Array[Any] = Array(5, hello, 1.5)
We don't see that an array containing an integer
,string
and double
is created. We see that an array of Any
is created. During array creation
, the scala compiler looked for the nearest common supertype in hierarchy
to satisfy the property of Array that it can hold elements of same type only
. And in this case, Any
being the supertype of all the classes, satisfies the condition. And, if the compiler can't find the common supertype, Array creation will fail.
Note that, it's not just for Array, same goes for other collections
that store same types
.for eg: List
scala> val list = List(5,"hello",1.5)
list: List[Any] = List(5, hello, 1.5)
what is the option we have in scala to store different data types?
As you can see that we are not able to preserve the type of elements
here in both List
and Array
. All the elements are being stored as Any
. For preserving types of elements and storing them together, scala provides us with Tuple
:
scala> val tuple = (5,"hello",1.5)
tuple: (Int, String, Double) = (5,hello,1.5)
Upvotes: 2
Reputation: 11587
As others have answered why Array[Any]
can have elements of types String, Boolean, Int etc. let me answer the below part of the question
if it is wrong then what is the option we have in scala to store different data types?*
The most obvious answer is the Shapeless library. Shapeless supports an advanced data-structure called HList
using which you can store heterogenous types in a list without losing the type information.
for example see the below snippet
scala> import shapeless.{::, HList, HNil}
import shapeless.{$colon$colon, HList, HNil}
scala> val list = 1 :: "a" :: true :: HNil
list: shapeless.::[Int,shapeless.::[String,shapeless.::[Boolean,shapeless.HNil]]] = 1 :: a :: true :: HNil
scala> list.head
res0: Int = 1 // notice the type of the element is Int and not Any
scala> list.tail.head
res1: String = a
scala> list.tail.tail.head
res2: Boolean = true
In the above code you have a val list
of type HList
with three elements of types Int
, String
and Boolean
. And when you retrieve the elements of the HList
the original type of the elements are preserved and you don't get a generic type like Any
as in the case of Array. This is possible because HList
stores not just data but the type information of the elements too and properly casts them on retrieval.
Upvotes: 0