Home > Net >  how Value type works in enum?
how Value type works in enum?

Time:07-25

what's a diff between these two snippets

  object Main extends Enumeration {

    val first : String = "Thriller"
    val second : String = "Horror"
    val third : String = "Comedy"
    val fourth : String = "Romance"

    // Main Method
    def main(args: Array[String]) {
      println(s" Movie Genres = ${Main.first}")
    }
  }

And

object Main extends Enumeration
{
    type Main = Value
     
    // Assigning values
    val first = Value("Thriller")
    val second = Value("Horror")
    val third = Value("Comedy")
    val fourth = Value("Romance")
     
    // Main method
    def main(args: Array[String])
    {
        println(s"Main Movie Genres = ${Main.values}")
    }
}

what benefit am getting by using type Main = Value in second code snippet ? I'm struggling to understand this even after reading alot online. Please share any simple understanding if possible.

Because in Java when we define this below code, all values (HEARTS, DIAMOND etc) are of CardSuit type, so can't we say that (first, second etc) are of Main type ?

enum CardSuit{
    HEARTS,
    DIAMONDS,
    CLUBS,
    SPADES,
}

Last is, Is there any way I could have more than 2 attributes assign to any enum's constants in scala ? For example val first = Value("Thriller", "movie, "london", "production")

CodePudding user response:

Enumeration used private constructors and other tricks to:

  • define type Value within your object that you extended with Enumeration
  • limited constructors so that they could only be called from within your object
  • make these constructors do side-effects so that each new value would append itself to the mutable list (which isn't mutable from outside)

This approach has several issues:

  1. when you do object MyEnum extends Enumeration your enumerations will NOT be defined as MyEnum type, but as MyEnum.Value
  2. if you want to use MyEnum as the name of enumeration, you have to use type alias type MyEnum = MyEnum.Value or type MyEnum = Value
  3. however the type of companion will still be MyEnum.Value.type instead of MyEnum.type. Aliases creating MyEnum.MyEnum and MyEnum.MyEnum.type are just silly
  4. each value is of the same type, so type level programming options are quite limited
  5. you cannot customize Value: let it inherit your type, add some field, store something else than String, not store anything...

Points 1. and 2. are the reasons people did the type aliasing. All 5 were the reasons people moves to sealed traits

sealed trait MyEnum extends Product with Serializable
object MyEnum {
  case object One extends MyEnum
  case object Two extends MyEnum
  case object Three extends MyEnum
}

they work better with pattern matching, derivation, it is easier to customize them (you just add things to common trait/common abstract class), etc.

In Scala 3 it got simplified to

enum MyEnum:
  case One, Two, Three

All in all, there is virtually 0 reasons to use Enumeration other than legacy code.

  • Related