JavaRush /Java Blog /Random-TW /Java 中的枚舉:如何使用該類別

Java 中的枚舉:如何使用該類別

在 Random-TW 群組發布
你好!在這篇文章中,我將向您介紹 Java 枚舉。想像一下,您被賦予了一項任務:創建一個實現星期幾的類別。乍一看,這並不複雜,您的程式碼將如下所示:
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 + '\'' +
               '}';
   }
}
一切似乎都很好,但有一個問題:您可以將任何文字傳遞給DayOfWeek類別的建構子。這樣,某人就可以創建星期幾「Frog」、「Cloud」或「azaza322」。這顯然不是我們期望的行為,因為一周中只有 7 天,而且每一天都有一個名字。因此,我們的任務是以某種方式限制「星期幾」類別的可能值的範圍。在 Java 1.5 之前,由於語言本身沒有現成的解決方案,開發人員被迫自己想出一個解決方案來解決這個問題。在那些日子裡,如果情況需要有限數量的值,他們會這樣做:
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 + '\'' +
               '}';
   }
}
這裡要注意的是:
  • 私有構造函數。如果建構函式被標記為private修飾符,則不能使用該建構函式建立該類別的物件。而且由於類別中只有一個建構函數,因此根本無法建立DayOfWeek物件。

    public class Main {
    
       		public static void main(String[] args) {
    
           			DayOfWeek sunday = new DayOfWeek();//error!
       		}
    }
  • 同時,該類別包含所需數量的公共靜態對象,這些對像以我們需要的方式初始化(​​日期的名稱是正確的)。

    這使得在其他類別中使用物件成為可能。

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

    結論:

    DayOfWeek{title='星期日'}

這種方法在很大程度上使我們能夠解決問題。我們每週有 7 天可以隨意支配,沒有人可以創造新的。這個解決方案是由 Joshua Bloch 在《Effective Java》一書中提出的。順便說一下,這本書非常酷,是所有 Java 開發人員的必讀之作。
如何使用枚舉類別 - 2
隨著 Java 1.5 的發布,該語言為此類情況引入了現成的解決方案 - Enum枚舉。 枚舉也是一個類別。但它是專門為解決與我們類似的問題而「量身定制」的:創造一定範圍內的有限價值。由於 Java 的創建者已經有了​​現成的範例(例如 C 語言,其中已經存在Enum),因此他們能夠創建最佳選項。

什麼是枚舉?

那麼,Java 中的 Enum是什麼呢?讓我們來看看同一個DayOfWeek的範例:
public enum DayOfWeek {

   SUNDAY,
   MONDAY,
   TUESDAY,
   WEDNESDAY,
   THURSDAY,
   FRIDAY,
   SATURDAY
}
它看起來已經簡單多了:) 在我們的Enum內部有 7 個具有靜態存取的常數。我們已經可以使用它來實現程式中的邏輯了。例如,讓我們寫一個程式來確定學生今天是否需要去學校。我們的學生將有自己的日常生活,由ScholarSchedule類別指定:
public class ScholarSchedule {

   private DayOfWeek dayOfWeek;
   //...other fields


   public DayOfWeek getDayOfWeek() {
       return dayOfWeek;
   }

   public void setDayOfWeek(DayOfWeek dayOfWeek) {
       this.dayOfWeek = dayOfWeek;
   }
}
日模式的dayOfWeek 變數決定今天是哪一天。這是我們學生的班級:
public class Scholar {

   private ScholarSchedule schedule;
   private boolean goToSchool;

   public void wakeUp() {

       if (this.schedule.getDayOfWeek() == DayOfWeek.SUNDAY) {
           System.out.println("Hooray, you can sleep some more!");
       } else {
           System.out.println("Damn, back to school :(");
       }
   }
}
wakeUp()方法中,我們使用枚舉來確定學生的進一步操作。我們甚至沒有詳細描述DayOfWeek中每個變數的含義,而且這是沒有必要的:星期幾的機制已經很明顯了,如果我們以當前的形式使用它,任何開發人員都會明白什麼正在您的程式碼中發生。Enum便利性的另一個例子是它的常數可以與switch 語句一起使用。例如,我們正在編寫一個嚴格飲食的程序,其中按天安排膳食:
public class VeryStrictDiet {
   public void takeLunch(DayOfWeek dayOfWeek) {
       switch (dayOfWeek) {
           case SUNDAY:
               System.out.println("Sunday lunch! Today you can even have a little sweet");
               break;
           case MONDAY:
               System.out.println("Monday Lunch: Chicken Noodles!");
               break;
           case TUESDAY:
               System.out.println("Tuesday, today is celery soup :(");
               break;
               //...and so on until the end
       }
   }
}
這是Enum 相對於 Java 1.5 之前使用的舊解決方案的 優勢之一:舊解決方案無法與switch一起使用。

關於 Enum 類,您還需要了解什麼?

枚舉類別是一個真正的類,具有它附帶的所有功能。例如,如果目前的星期幾的實作對您來說還不夠,您可以為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 + '\'' +
               '}';
   }
}
我們的Enum 常數現在有一個title字段、一個 getter 和一個重寫的toString方法。與常規類別相比,Enum有一個嚴重的限制——它不能被繼承。此外,枚舉還有其獨特的方法:
  • value() :傳回Enum中儲存的所有值的陣列:

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

    結論:

    [DayOfWeek{title='星期日'}、DayOfWeek{title='星期一'}、DayOfWeek{title='星期二'}、DayOfWeek{title='星期三'}、DayOfWeek{title='星期四'}、DayOfWeek{title = '星期五'},DayOfWeek{title='星期六'}]

  • ordinal():傳回常數的序數。倒數計時從零開始:

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

    結論:

    0

  • valueOf():傳回與給定名稱對應的Enum物件:

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

    結論:

    DayOfWeek{title='星期日'}

注意:我們將Enum元素的名稱大寫,因為它們是常數並且被指定為常數,而不是駝峰命名法
留言
TO VIEW ALL COMMENTS OR TO MAKE A COMMENT,
GO TO FULL VERSION