CodeGym /Java Blog /अनियमित /Enum। व्यावहारिक उदाहरण। कंस्ट्रक्टर और तरीके जोड़ना
John Squirrels
स्तर 41
San Francisco

Enum। व्यावहारिक उदाहरण। कंस्ट्रक्टर और तरीके जोड़ना

अनियमित ग्रुप में प्रकाशित
नमस्ते! आज हम जावा के विशेष डेटा प्रकारों में से एक के बारे में बात करेंगे: Enum("गणना" के लिए संक्षिप्त)। यह क्या खास बनाता है? आइए कल्पना करें कि कार्यक्रम में "महीनों" को लागू करने के लिए हमें क्या चाहिए। Enum।  व्यावहारिक उदाहरण।  कंस्ट्रक्टर और तरीके जोड़ना - 1 समस्याग्रस्त नहीं लगता, है ना? हमें केवल यह निर्धारित करने की आवश्यकता है कि किसी भी महीने में कौन से गुण हैं। शायद हमें सबसे पहले महीने का नाम और उसमें दिनों की संख्या चाहिए। समाधान बहुत आसान दिखता है:

public class Month {

   private String name;
   private int daysCount;

   public Month(String name, int daysCount) {
       this.name = name;
       this.daysCount = daysCount;
   }

   public String getName() {
       return name;
   }

   public void setName(String name) {
       this.name = name;
   }

   public int getDaysCount() {
       return daysCount;
   }

   public void setDaysCount(int daysCount) {
       this.daysCount = daysCount;
   }

   @Override
   public String toString() {
       return "Month{" +
               "name='" + name + '\'' +
               ", daysCount=" + daysCount +
               '}';
   }
}
पूरा शाबांग! हमारे पास एक Monthवर्ग, आवश्यक फ़ील्ड, गेट्टर/सेटर और toString(). जब तक, निश्चित रूप से, हमें equals()और जोड़ने की आवश्यकता नहीं हैhashCode()पूर्ण सुख प्राप्त करने के लिए :) लेकिन यहाँ हमें एक वैचारिक समस्या है। जैसा कि आपको शायद याद होगा, OOP का एक मुख्य लाभ यह है कि यह वास्तविक दुनिया से संस्थाओं को मॉडल करना आसान बनाता है। एक कुर्सी, एक कार, एक ग्रह - सामान्य जीवन से इन सभी अवधारणाओं को अमूर्तता की मदद से एक कार्यक्रम में आसानी से दर्शाया जाता है। समस्या यह है कि कुछ वास्तविक दुनिया की संस्थाओं के मूल्यों की एक सीमित सीमा होती है। एक वर्ष में केवल 4 ऋतुएँ होती हैं। एक सप्तक में केवल 8 स्वर होते हैं। कैलेंडर में सिर्फ 12 महीने होते हैं। और ओशन के 11 के डैनी ओशन के सिर्फ 11 दोस्त हैं (हालाँकि इससे कोई फर्क नहीं पड़ता :)) क्या मायने रखता है कि एक साधारण जावा वर्ग इन संस्थाओं को मॉडल करने और उनकी प्राकृतिक सीमाओं को लागू करने में सक्षम नहीं है। हमाराMonthकक्षा में सभी आवश्यक फ़ील्ड हैं। लेकिन अगर कोई अन्य प्रोग्रामर इसका उपयोग करता है, तो कोई भी उसे पूरी तरह से पागल वस्तु बनाने से नहीं रोक सकता है:

public class Main {

   Month month1 = new Month("lolkek", 322);
   Month month2 = new Month("yahoooooooooooo", 12345);

}
यदि यह हमारे कोड में दिखाई देता है, तो अपराधी को ढूंढना आसान नहीं होगा! एक ओर, ऑब्जेक्ट बनाने वाले प्रोग्रामर को यह महसूस हो सकता है कि Monthकक्षा का अर्थ "एक वर्ष में महीना" है और इस तरह की बकवास नहीं लिखता है। दूसरी ओर, प्रोग्रामर केवल क्लास डिज़ाइनर द्वारा प्रदान की गई क्षमताओं का लाभ उठा रहा है। क्या मनमाना नाम और दिनों की संख्या निर्दिष्ट करना संभव है? ठीक यही हमें मिला है। ऐसे में हमें क्या करना चाहिए? ईमानदारी से, जावा 1.5 जारी होने से पहले, प्रोग्रामर को रचनात्मक होना पड़ा :) उन दिनों, उन्होंने इस तरह की संरचनाएं बनाईं:

public class Month {

   private String name;
   private int daysCount;

   private Month(String name, int daysCount) {
       this.name = name;
       this.daysCount = daysCount;
   }

   public static Month JANUARY = new Month("January", 31);
   public static Month FEBRUARY = new Month("February", 28);
   public static Month MARCH = new Month("March", 31);

   @Override
   public String toString() {
       return "Month{" +
               "name='" + name + '\'' +
               ", daysCount=" + daysCount +
               '}';
   }
}
यहां हमने उदाहरण को छोटा करने के लिए महीनों की संख्या को बारह से घटाकर तीन कर दिया है। इस तरह के डिजाइनों ने समस्या को हल करना संभव बना दिया। ऑब्जेक्ट बनाने की क्षमता एक निजी कंस्ट्रक्टर तक सीमित थी:

private Month(String name, int daysCount) {
       this.name = name;
       this.daysCount = daysCount;
   }
क्लास का उपयोग करने वाले प्रोग्रामर केवल Monthऑब्जेक्ट नहीं बना सकते थे। उन्हें क्लास डेवलपर द्वारा प्रदान की गई अंतिम स्थैतिक वस्तुओं का उपयोग करना था। उदाहरण के लिए, इस तरह:

public class Main {

   public static void main(String[] args) {

       Month january = Month.JANUARY;
       System.out.println(january);
   }

}
लेकिन, जावा डेवलपर्स ने मौजूदा समस्या की ओर ध्यान आकर्षित किया। बेशक, यह बहुत अच्छा है कि प्रोग्रामर भाषा में उपलब्ध उपकरणों का उपयोग करके एक समाधान के साथ आने में सक्षम थे, लेकिन यह बहुत आसान नहीं लगता! नौसिखियों के लिए भी एक स्पष्ट समाधान की आवश्यकता थी। और इसलिए Enumजावा में दिखाई दिया। मूल रूप से, Enumएक जावा वर्ग है जो वस्तु मूल्यों का एक सीमित सेट प्रदान करता है। यहाँ यह कैसा दिखता है:

public enum Month {
  
   JANUARY,
   FEBRUARY,
   MARCH
}
परिभाषा में, हमने संकेत दिया कि यह Enumएक जावा वर्ग है, लेकिन क्या यह वास्तव में सच है? हाँ, और हम इसे सत्यापित भी कर सकते हैं। उदाहरण के लिए, हमारे Monthएनम को किसी अन्य वर्ग का उत्तराधिकारी बनाने का प्रयास करें:

public abstract class AbstractMonth {
}

// Error! The extends clause cannot be used with an enum
public enum Month extends AbstractMonth {

   JANUARY,
   FEBRUARY,
   MARCH
}
ऐसा क्यों होता है? जब हम लिखते हैं:

public enum Month
संकलक इस कथन को निम्नलिखित कोड में परिवर्तित करता है:

public Class Month extends Enum
जैसा कि आप पहले से ही जानते हैं, जावा एकाधिक वंशानुक्रम का समर्थन नहीं करता है। इसलिए, हम उत्तराधिकारी नहीं हो सकते AbstractMonth। इस नए निर्माण, Enum, का उपयोग कैसे किया जा सकता है? और यह खेतों के साथ पुराने निर्माण से कैसे भिन्न है static final? खैर, एक उदाहरण के रूप में, पुराने निर्माण ने हमें switchबयानों में अपने स्वयं के मूल्यों के सेट का उपयोग नहीं करने दिया। कल्पना कीजिए कि हम एक ऐसा कार्यक्रम बनाना चाहते हैं जो हमें हर महीने मनाई जाने वाली छुट्टियों की याद दिलाए:

public class HolidayReminder {

   public void printHolidays(Month month) {

       switch (month) {

           // Error!
           case JANUARY:
       }
   }
}
जैसा कि आप देख सकते हैं, संकलक यहाँ एक त्रुटि फेंकता है। लेकिन एक बार enumजावा 1.5 में दिखाई देने के बाद, सब कुछ बहुत आसान हो गया:

public enum Month {

   JANUARY,
   FEBRUARY,
   MARCH
}

public class HolidayReminder {

   public void printHolidays(Month month) {

       switch (month) {
          
           case JANUARY:
               System.out.println("New Year's Day is January 1st!");
               break;
           case FEBRUARY:
               System.out.println("Valentine's Day is February 14th!");
               break;
           case MARCH:
               System.out.println("Saint Patrick's Day is March 17th!");
               break;
       }
   }
}


public class Main {

   public static void main(String[] args) {

       HolidayReminder reminder = new HolidayReminder();
       reminder.printHolidays(Month.JANUARY);

   }

}
कंसोल आउटपुट:

New Year's Day is January 1st!
ध्यान दें कि Enumवस्तुओं तक पहुंच स्थिर बनी हुई है, ठीक वैसे ही जैसे जावा 1.5 से पहले थी। Monthहमें महीनों तक पहुँचने के लिए कोई वस्तु बनाने की आवश्यकता नहीं है । Enums के साथ काम करते समय, यह भूलना बहुत महत्वपूर्ण है कि यह Enumएक पूर्ण वर्ग है। इसका मतलब है कि, यदि आवश्यक हो, तो आप इसमें कंस्ट्रक्टर और विधियों को परिभाषित कर सकते हैं। उदाहरण के लिए, पिछले कोड खंड में, हमने केवल मान निर्दिष्ट किए हैं: जनवरी, फरवरी, मार्च। हालाँकि, हम Monthइस तरह से अपने एनम का विस्तार कर सकते हैं:

public enum Month {

   JANUARY("January", 31),
   FEBRUARY("February", 28),
   MARCH("March", 31),
   APRIL("April", 30),
   MAY("May", 31),
   JUNE("June", 30),
   JULY("July", 31),
   AUGUST("August", 31),
   SEPTEMBER("September", 30),
   OCTOBER("October", 31),
   NOVEMBER("November", 30),
   DECEMBER("December", 31);

   private String name;
   private int daysCount;

   Month(String name, int daysCount) {
       this.name = name;
       this.daysCount = daysCount;
   }

   public static Month[] getWinterMonths() {

       return new Month[]{DECEMBER, JANUARY, FEBRUARY};
   }

   public static Month[] getSummerMonths() {

       return new Month[]{JUNE, JULY, AUGUST};
   }

   public String getName() {
       return name;
   }

   public void setName(String name) {
       this.name = name;
   }

   public int getDaysCount() {
       return daysCount;
   }

   public void setDaysCount(int daysCount) {
       this.daysCount = daysCount;
   }

   @Override
   public String toString() {
       return "Month{" +
               "name='" + name + '\'' +
               ", daysCount=" + daysCount +
               '}';
   }
}
यहां हमने अपने enum2 फील्ड्स (महीने का नाम और दिनों की संख्या) दिए हैं, एक कंस्ट्रक्टर जो इन फील्ड्स, गेट्टर/सेटर्स, मेथड toString()और 2 स्टैटिक मेथड्स का इस्तेमाल करता है। जैसा कि आप देख सकते हैं, इसमें कोई समस्या नहीं थी। फिर, Enumवास्तव में एक पूर्ण वर्ग है:

import java.util.Arrays;

public class Main {

   public static void main(String[] args) {

       System.out.println(Arrays.toString(Month.getSummerMonths()));

   }

}
कंसोल आउटपुट:

[Month{name='June', daysCount=30}, Month{name='July', daysCount=31}, Month{name='August', daysCount=31}]
अंत में, मैं जोशुआ बलोच द्वारा "प्रभावी जावा" नामक एक अत्यंत उपयोगी जावा पुस्तक की सिफारिश करना चाहता हूं । Enum।  व्यावहारिक उदाहरण।  कंस्ट्रक्टर और तरीके जोड़ना - 3लेखक जावा के रचनाकारों में से एक है, इसलिए आप निश्चित रूप से उसकी सलाह पर भरोसा कर सकते हैं कि भाषा के उपकरणों का सही और सक्षम उपयोग कैसे करें :) हमारे पाठ के संबंध में, मैं अनुशंसा करता हूं कि आप पुस्तक के अध्याय पर विशेष ध्यान दें Enum। पढ़ने का आनंद लो! :)
टिप्पणियां
TO VIEW ALL COMMENTS OR TO MAKE A COMMENT,
GO TO FULL VERSION