CodeGym/Java Blog/Java Classes/Enum class in Java
Author
Milan Vucic
Programming Tutor at Codementor.io

Enum class in Java

Published in the Java Classes group
members
Hi! In this article we are going to tell you about Java Enums. Imagine that you've been given the following task: create a class that implements the days of the week. At first glance, this seems rather straightforward. Your code would look something like this:
public class DayOfWeek {

   private String title;

   public DayOfWeek(String title) {
       this.title = title;
   }

   public static void main(String[] args) {
       DayOfWeek dayOfWeek = new DayOfWeek("Saturday");
       System.out.println(dayOfWeek);
   }

   @Override
   public String toString() {
       return "DayOfWeek{" +
               "title='" + title + '\'' +
               '}';
   }
}
Everything seems to be fine, but there is one problem: you can pass any text to the constructor of the DayOfWeek class. That means someone could create a day of the week named "Frog", "Cloud" or "azaza322". This is clearly not the behavior that we expect, since there are only 7 real days of the week, and each of them has a specific name. Therefore, our task is to somehow limit the range of possible values for the DayOfWeek class. Before Java 1.5 came along, developers had to independently invent their own solutions to this problem, since the language didn't have a ready-made solution. In those days, if programmers needed to limit the number of values, they did this:
public class DayOfWeek {

   private String title;

   private DayOfWeek(String title) {
       this.title = title;
   }

   public static DayOfWeek SUNDAY = new DayOfWeek("Sunday");
   public static DayOfWeek MONDAY = new DayOfWeek("Monday");
   public static DayOfWeek TUESDAY = new DayOfWeek("Tuesday");
   public static DayOfWeek WEDNESDAY = new DayOfWeek("Wednesday");
   public static DayOfWeek THURSDAY = new DayOfWeek("Thursday");
   public static DayOfWeek FRIDAY = new DayOfWeek("Friday");
   public static DayOfWeek SATURDAY = new DayOfWeek("Saturday");

   @Override
   public String toString() {
       return "DayOfWeek{" +
               "title='" + title + '\'' +
               '}';
   }
}
Here's what you should notice:
  • The constructor is private. If a constructor is marked with the private modifier, it cannot be used to create an object. And since the class has only one constructor, no DayOfWeek objects can ever be created.

    public class Main {
    
       		public static void main(String[] args) {
    
           			DayOfWeek sunday = new DayOfWeek(); // Error!
       		}
    }

  • Of course, the class does have the required number of public static objects, which were correctly initialized (using the correct names of the days of the week).

    This allowed these objects to be used in other classes.

    public class Person {
    
       		public static void main(String[] args) {
    
           			DayOfWeek sunday = DayOfWeek.SUNDAY;
    
           			System.out.println(sunday);
      		 }
    }

    Output:

    DayOfWeek{title = 'Sunday'}

This approach largely solves the problem. We have 7 days of the week at our disposal, and nobody can create new ones. This solution was offered by Joshua Bloch in his book Effective Java. By the way, that book is very cool and a must-read for any Java developer. How to use the Enum class - 2With the release of Java 1.5, the language gained a ready-made solution for such situations: Java Enums. Enum in Java is also a class. It is specially "fine-tuned" to solving problems like this, i.e. creating a certain limited range of values. Java's creators already had ready examples (for example, C already had enum), so they were able to create the best variant.

So what is Java Enum?

Let's revisit our DayOfWeek example:
public enum DayOfWeek {

   SUNDAY,
   MONDAY,
   TUESDAY,
   WEDNESDAY,
   THURSDAY,
   FRIDAY,
   SATURDAY
}
Now that looks a lot simpler :) Internally, our Enum has 7 static constants. And that's something we can use it to implement a program. For example, let's write a program that determines whether a student needs to go to school today. Our student will have a daily schedule, represented by the StudentSchedule class:
public class StudentSchedule {

   private DayOfWeek dayOfWeek;
   // ... other fields


   public DayOfWeek getDayOfWeek() {
       return dayOfWeek;
   }

   public void setDayOfWeek(DayOfWeek dayOfWeek) {
       this.dayOfWeek = dayOfWeek;
   }
}
The schedule object's dayOfWeek variable determines which day is today. And here's our student class:
public class Student {

   private StudentSchedule schedule;
   private boolean goToSchool;

   public void wakeUp() {

       if (this.schedule.getDayOfWeek() == DayOfWeek.SUNDAY) {
           System.out.println("Hooray, you can sleep more!");
       } else {
           System.out.println("Damn, time for school again :(");
       }
   }
}
In the wakeUp() method, we use Java Enum to determine what the student should do next. We didn't even provide details about each field in DayOfWeek, and we don't need to: it's obvious how the days of the week are supposed to work. If we use it in its current form, any developer would understand what is happening in our code. Another example of the convenience of Enum is that its constants can be used with the switch statement. For example, let's write a program for a strict diet, in which dishes are scheduled by day:
public class VeryStrictDiet {
   public void takeLunch(DayOfWeek dayOfWeek) {
       switch (dayOfWeek) {
           case SUNDAY:
               System.out.println("Sunday Dinner! You can even enjoy something a little sweet today.");
               break;
           case MONDAY:
               System.out.println("Lunch for Monday: chicken noodle soup!");
               break;
           case TUESDAY:
               System.out.println("Tuesday, today it's celery soup :(");
               break;
               //... and so on to the end
       }
   }
}
This is one of Enums advantages over the old solution used before Java 1.5 — the old solution could not be used with switch. What else do you need to know about Enum? Enum is a real class with all the possibilities that this entails. For example, if the current implementation of the days of the week is inadequate, you can add variables, constructors, and methods to DayOfWeek:
public enum DayOfWeek {

   SUNDAY ("Sunday"),
   MONDAY ("Monday"),
   TUESDAY ("Tuesday"),
   WEDNESDAY ("Wednesday"),
   THURSDAY ("Thursday"),
   FRIDAY ("Friday"),
   SATURDAY ("Saturday");

   private String title;

   DayOfWeek(String title) {
       this.title = title;
   }

   public String getTitle() {
       return title;
   }

   @Override
   public String toString() {
       return "DayOfWeek{" +
               "title='" + title + '\'' +
               '}';
   }
}
Now our Enum constants have a title field, getter, and overridden toString method. Compared to regular classes, one serious limitation was placed on Enum — it cannot be inherited. Additionally, enumerations have characteristic methods:
  • values(): returns an array of all the values in the Enum:

    public static void main(String[] args) {
       		System.out.println(Arrays.toString(DayOfWeek.values()));
    }

    Output:

    [DayOfWeek{title = 'Sunday'}, DayOfWeek{title = 'Monday'}, DayOfWeek{title = 'Tuesday'}, DayOfWeek{title = 'Wednesday'}, DayOfWeek{title = 'Thursday'}, DayOfWeek{title = 'Friday'}, DayOfWeek{title = 'Saturday'}]

  • ordinal(): returns the ordinal number of the constant. The numbering starts from zero:

    public static void main(String[] args) {
    
       		int sundayIndex = DayOfWeek.SUNDAY.ordinal();
       		System.out.println(sundayIndex);
    }

    Output:

    0

  • valueOf(): returns the Enum object that corresponds to the passed name:

    public static void main(String[] args) {
       DayOfWeek sunday = DayOfWeek.valueOf("SUNDAY");
       System.out.println(sunday);
    }

    Output:

    DayOfWeek{title = 'Sunday'}

Note: we use uppercase letters to specify Enum fields. These are constants so they use all-caps rather than camelCase.
Comments (8)
  • Popular
  • New
  • Old
You must be signed in to leave a comment
Mateusz
Level 15 , Poland, Poland
21 July 2022, 19:21
I don’t know about you guys, but I need practice.
Agent Smith
Level 38
23 August 2020, 16:20
I hope to see a truck load of exercises for this one. ^_^
Peter Schrijver
Level 23 , Hilversum, Netherlands
11 June 2020, 14:28
Nice information
Fadi Alsaidi
Level 34 , Carrollton, TX, USA
22 December 2019, 02:25
So basically the Calendar is an Enum.
Renat Mukhametshin
Level 16 , Pervouralsk, Russain Federation
8 August 2019, 09:40
good practice need for this topic
Dusernajder
Level 20 , Budapest, Hungary
3 August 2019, 18:12
So are you assigning values to static constant variables in the enum class like this: SUNDAY ("Sunday"), MONDAY ("Monday"), TUESDAY ("Tuesday"), WEDNESDAY ("Wednesday"), THURSDAY ("Thursday"), FRIDAY ("Friday"), SATURDAY ("Saturday"); Or lets say, SUNDAY itself holds a value of SUNDAY, or are those Strings for the toString() method?
Isaiah Burkes
Level 16 , Tampa, United States
12 December 2019, 06:08
Yeah it looks like you're right about the strings being for the toString() method.
DayOfWeek(String title) {
      this.title = title;
  }
This constructor gives DayOfWeek enum values a title variable that is used in the toString() method.
Jonaskinny Java Developer at Sandmedia
20 February 2022, 03:51
the key to understanding enum is that it is a keyword (lowercase enum) in the java language to specify an enumeration (one of the values defined in the given enum). When we declare public enum SomeNameForEnum {} we get our declared values (SUNDAY,MONDAY,etc) as an enum of type SomeNameForrEnum. This is because of how Sun implemented Enum (uppercase name) in that every Enum extends Enum ... so only Sun gets to decide what happens inside the parent Enum, and we can only use the language keyword enum, which under the hood creates a Enum object, sets Enum.name=what we named our enum (SomeNameForEnum), and it stores an int to represent this Enum in the system to enforce uniqueness (singleton pattern), and so when you say SomeNameForEnum.SUNDAY what you get is Enum.getName() called on the object that you can not see, that is the Enum, managed by the JVM, and we use enum in our code to have the JVM resolve that value to the underlying member of Enum. Think of enum as a function call that equates to "get the name of this enum Im passing in, use that to get the int ID the JVM assigned to that Enum, map to the singleton method getInstance(), then make sure what is passed in equates to one value defined in that Enum (that we defined in our code by calling enum). To understand what SUNDAY is in the above enum, try this... boolean isString = DayOfWeek.SUNDAY instanceof String; <- wont compile, cant try instanceof String since it will fail to cast to String to check, so you cant even check. It fails before it can even say false. DayOfWeek.SUNDAY is an instanceof Enum (the java class we can not access directly). The JVM maps each entry in the Enum as an Enum of the declared type.