JavaRush /Blog Java /Random-PL /Enum w Javie: jak korzystać z klasy

Enum w Javie: jak korzystać z klasy

Opublikowano w grupie Random-PL
Cześć! W tym artykule opowiem o wyliczeniach Java. Wyobraź sobie, że otrzymałeś zadanie: utwórz klasę implementującą dni tygodnia . Na pierwszy rzut oka nie ma w tym nic skomplikowanego, a Twój kod będzie wyglądał mniej więcej tak:
public class DayOfWeek {

   private String title;

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

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

   @Override
   public String toString() {
       return "DayOfWeek{" +
               "title='" + title + '\'' +
               '}';
   }
}
I wszystko wydaje się być w porządku, jest jednak jeden problem: możesz przekazać dowolny tekst konstruktorowi klasy DayOfWeek . W ten sposób każdy może stworzyć dzień tygodnia „Żaba”, „Chmura” lub „azaza322”. Zdecydowanie nie jest to zachowanie, jakiego oczekujemy, ponieważ tak naprawdę dni tygodnia jest tylko 7, a każdy z nich ma swoją nazwę. Dlatego naszym zadaniem jest w jakiś sposób ograniczyć zakres możliwych wartości dla klasy „ dzień tygodnia ”. Przed Javą 1.5 programiści byli zmuszeni samodzielnie znaleźć rozwiązanie tego problemu, ponieważ w samym języku nie było gotowego rozwiązania. W tamtych czasach, jeśli sytuacja wymagała ograniczonej liczby wartości, robiono to:
public class DayOfWeek {

   private String title;

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

   public static DayOfWeek SUNDAY = new DayOfWeek("Niedziela");
   public static DayOfWeek MONDAY = new DayOfWeek("Poniedziałek");
   public static DayOfWeek TUESDAY = new DayOfWeek("Wtorek");
   public static DayOfWeek WEDNESDAY = new DayOfWeek("Środa");
   public static DayOfWeek THURSDAY = new DayOfWeek("Czwartek");
   public static DayOfWeek FRIDAY = new DayOfWeek("Piątek");
   public static DayOfWeek SATURDAY = new DayOfWeek("Sobota");

   @Override
   public String toString() {
       return "DayOfWeek{" +
               "title='" + title + '\'' +
               '}';
   }
}
Na co warto tutaj zwrócić uwagę:
  • Prywatny konstruktor. Jeśli konstruktor jest oznaczony modyfikatorem private , nie można utworzyć obiektu klasy przy użyciu tego konstruktora. A ponieważ w tej klasie jest tylko jeden konstruktor, w ogóle nie można utworzyć obiektu DayOfWeek .

    public class Main {
    
       		public static void main(String[] args) {
    
           			DayOfWeek sunday = new DayOfWeek();//błąd!
       		}
    }
  • Jednocześnie klasa zawierała wymaganą liczbę publicznych obiektów statycznych , które zostały zainicjowane w taki sposób w jaki potrzebowaliśmy (nazwy dni są prawidłowe).

    Umożliwiło to wykorzystanie obiektów w innych klasach.

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

    Wniosek:

    Dzień Tygodnia{title='Niedziela'}

Takie podejście w dużej mierze pozwoliło nam rozwiązać problem. Do dyspozycji mieliśmy 7 dni tygodnia i nikt nie potrafił tworzyć nowych. Rozwiązanie to zaproponował Joshua Bloch w książce Efektywna Java . Nawiasem mówiąc, książka jest bardzo fajna i obowiązkowa dla każdego programisty Java.
Jak korzystać z klasy Enum - 2
Wraz z wydaniem Java 1.5 język wprowadził gotowe rozwiązanie na takie sytuacje - wyliczenie Enum . Enum to także klasa. Ale jest specjalnie „dostosowany” do rozwiązywania problemów podobnych do naszych: tworzenia pewnego ograniczonego zakresu wartości. Ponieważ twórcy Javy mieli już gotowe przykłady (powiedzmy język C, w którym istniało już Enum ), udało im się stworzyć opcję optymalną.

Co to jest wyliczenie?

Czym więc jest Enum w Javie ? Spójrzmy na przykład tego samego DayOfWeek :
public enum DayOfWeek {

   SUNDAY,
   MONDAY,
   TUESDAY,
   WEDNESDAY,
   THURSDAY,
   FRIDAY,
   SATURDAY
}
To już wygląda o wiele prościej :) Wewnątrz naszego Enum znajduje się 7 stałych z dostępem statycznym. Możemy już za jego pomocą zaimplementować logikę w programie. Na przykład napiszmy program, który określi, czy uczeń musi dzisiaj iść do szkoły. Nasz uczeń będzie miał swój własny rozkład dnia, wyznaczony przez klasę ScholarSchedule :
public class ScholarSchedule {

   private DayOfWeek dayOfWeek;
   //...inne pola


   public DayOfWeek getDayOfWeek() {
       return dayOfWeek;
   }

   public void setDayOfWeek(DayOfWeek dayOfWeek) {
       this.dayOfWeek = dayOfWeek;
   }
}
Zmienna dayOfWeek w trybie dziennym określa, jaki jest dzień. A oto klasa naszej uczennicy:
public class Scholar {

   private ScholarSchedule schedule;
   private boolean goToSchool;

   public void wakeUp() {

       if (this.schedule.getDayOfWeek() == DayOfWeek.SUNDAY) {
           System.out.println("Hurra, możesz jeszcze trochę pospać!");
       } else {
           System.out.println("Cholera, wracamy do szkoły :(");
       }
   }
}
W metodzie wakeUp() za pomocą Enum określamy dalsze działania ucznia. Nie opisywaliśmy nawet szczegółowo, co oznacza każda zmienna w DayOfWeek , a to nie jest konieczne: mechanizm dni tygodnia jest już oczywisty i jeśli zastosujemy go w obecnej formie, każdy programista zrozumie, co dzieje się w twoim kodzie. Innym przykładem wygody Enum jest to, że jego stałych można używać z instrukcją switch . Przykładowo piszemy program na ścisłą dietę, w której posiłki rozłożone są według dnia:
public class VeryStrictDiet {
   public void takeLunch(DayOfWeek dayOfWeek) {
       switch (dayOfWeek) {
           case SUNDAY:
               System.out.println("Niedzielny obiad! Dziś można nawet napić się trochę słodkości");
               break;
           case MONDAY:
               System.out.println(„Poniedziałkowy lunch: makaron z kurczakiem!”);
               break;
           case TUESDAY:
               System.out.println("Wtorek, dziś zupa selerowa :(");
               break;
               //... i tak dalej aż do końca
       }
   }
}
Jest to jedna z zalet Enum w porównaniu ze starym rozwiązaniem, które było używane przed Javą 1.5: starego rozwiązania nie można było używać z przełącznikiem .

Co jeszcze musisz wiedzieć o klasie Enum?

Klasa Enum to prawdziwa klasa ze wszystkimi związanymi z nią możliwościami. Przykładowo, jeśli obecna implementacja dni tygodnia nie jest dla Ciebie wystarczająca, możesz dodać zmienne, konstruktory i metody do DayOfWeek :
public enum DayOfWeek {

   SUNDAY ("Niedziela"),
   MONDAY ("Poniedziałek"),
   TUESDAY ("Wtorek"),
   WEDNESDAY ("Środa"),
   THURSDAY ("Czwartek"),
   FRIDAY ("Piątek"),
   SATURDAY ("Sobota");

   private String title;

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

   public String getTitle() {
       return title;
   }

   @Override
   public String toString() {
       return "DayOfWeek{" +
               "title='" + title + '\'' +
               '}';
   }
}
Stałe naszego Enum mają teraz pole tytułu , moduł pobierający i zastąpioną metodę toString . W porównaniu do zwykłych klas, Enum ma jedno poważne ograniczenie - nie można po nim dziedziczyć. Ponadto wyliczenia mają unikalne dla siebie metody:
  • wartości() : zwraca tablicę wszystkich wartości przechowywanych w Enum :

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

    Wniosek:

    [Dzień Tygodnia{title='Niedziela'}, Dzień Tygodnia{title='Poniedziałek'}, Dzień Tygodnia{title='Wtorek'}, Dzień Tygodnia{title='Środa'}, Dzień Tygodnia{title='Czwartek'}, Dzień Tygodnia{title= „piątek”}, dzień tygodnia{title='sobota'}]

  • ordinal() : zwraca liczbę porządkową stałej. Odliczanie zaczyna się od zera:

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

    Wniosek:

    0

  • valueOf() : Zwraca obiekt Enum odpowiadający podanej nazwie:

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

    Wniosek:

    Dzień Tygodnia{title='Niedziela'}

Zwróć uwagę:Nazwy elementów Enum piszemy wielką literą , ponieważ są to stałe i są oznaczone jako stałe, a nie camelCase .
Komentarze
TO VIEW ALL COMMENTS OR TO MAKE A COMMENT,
GO TO FULL VERSION