एक इरादे (सबसे अच्छा समाधान) के माध्यम से एनम या ऑब्जेक्ट पास करना


221

मेरे पास एक गतिविधि है जब दो अलग-अलग ArrayLists तक पहुंच की आवश्यकता होती है। दोनों सूचियाँ अलग-अलग वस्तुएँ हैं जिन्हें मैंने स्वयं बनाया है।

मूल रूप से मुझे इन वस्तुओं को एक इरादे से गतिविधि में पारित करने का एक तरीका चाहिए। मैं addExtras () का उपयोग कर सकता हूं लेकिन इसके लिए Parceable संगत क्लास की आवश्यकता है। मैं अपनी कक्षाओं को क्रमिक रूप से उत्तीर्ण कर सकता था, लेकिन जैसा कि मैं समझता हूं कि यह कार्यक्रम धीमा कर देता है।

मेरे विकल्प क्या हैं?

क्या मैं एनम पास कर सकता हूं?

एक तरफ के रूप में: एक इंटेंट से एक गतिविधि कंस्ट्रक्टर के मापदंडों को पारित करने का एक तरीका है?


शायद मुझे कुछ याद आ रहा है, लेकिन एक एरेलेस्ट से जुड़ी एक दुश्मनी कैसे है?
मार्टिन कोंकणी

जवाबों:


558

यह एक पुराना सवाल है, लेकिन हर कोई यह उल्लेख करने में विफल रहता है कि एनम वास्तव में हैं Serializableऔर इसलिए पूरी तरह से एक अतिरिक्त के रूप में एक इरादे में जोड़ा जा सकता है। ऐशे ही:

public enum AwesomeEnum {
  SOMETHING, OTHER;
}

intent.putExtra("AwesomeEnum", AwesomeEnum.SOMETHING);

AwesomeEnum result = (AwesomeEnum) intent.getSerializableExtra("AwesomeEnum");

स्थिर या अनुप्रयोग-विस्तृत चर का उपयोग करने का सुझाव वास्तव में एक बुरा विचार है। यह वास्तव में आपकी गतिविधियों को एक राज्य प्रबंधन प्रणाली में जोड़े रखता है, और इसे बनाए रखना, डिबग करना और समस्या को बाध्य करना कठिन है।


विकल्प:

इस तथ्य के बारे में tedzyc द्वारा एक अच्छी बात बताई गई कि ओडरिक द्वारा प्रदान किया गया समाधान आपको एक त्रुटि देता है। हालांकि, प्रस्तावित विकल्प थोड़ा बोझिल है (यहां तक ​​कि जेनरिक का उपयोग करके)।

यदि आप वास्तव में एक इरादे में जोड़ने के प्रदर्शन के बारे में चिंतित हैं तो मैं इसके बजाय इन विकल्पों का प्रस्ताव करता हूं:

विकल्प 1:

public enum AwesomeEnum {
  SOMETHING, OTHER;
  private static final String name = AwesomeEnum.class.getName();
  public void attachTo(Intent intent) {
    intent.putExtra(name, ordinal());
  }
  public static AwesomeEnum detachFrom(Intent intent) {
    if(!intent.hasExtra(name)) throw new IllegalStateException();
    return values()[intent.getIntExtra(name, -1)];
  }
}

उपयोग:

// Sender usage
AwesomeEnum.SOMETHING.attachTo(intent);
// Receiver usage
AwesomeEnum result = AwesomeEnum.detachFrom(intent);

विकल्प 2: (सामान्य, पुन: प्रयोज्य और enum से decoupled)

public final class EnumUtil {
    public static class Serializer<T extends Enum<T>> extends Deserializer<T> {
        private T victim;
        @SuppressWarnings("unchecked") 
        public Serializer(T victim) {
            super((Class<T>) victim.getClass());
            this.victim = victim;
        }
        public void to(Intent intent) {
            intent.putExtra(name, victim.ordinal());
        }
    }
    public static class Deserializer<T extends Enum<T>> {
        protected Class<T> victimType;
        protected String name;
        public Deserializer(Class<T> victimType) {
            this.victimType = victimType;
            this.name = victimType.getName();
        }
        public T from(Intent intent) {
            if (!intent.hasExtra(name)) throw new IllegalStateException();
            return victimType.getEnumConstants()[intent.getIntExtra(name, -1)];
        }
    }
    public static <T extends Enum<T>> Deserializer<T> deserialize(Class<T> victim) {
        return new Deserializer<T>(victim);
    }
    public static <T extends Enum<T>> Serializer<T> serialize(T victim) {
        return new Serializer<T>(victim);
    }
}

उपयोग:

// Sender usage
EnumUtil.serialize(AwesomeEnum.Something).to(intent);
// Receiver usage
AwesomeEnum result = 
EnumUtil.deserialize(AwesomeEnum.class).from(intent);

विकल्प 3 (कोटलिन के साथ):

थोड़ी देर हो गई है, लेकिन अब से हमारे पास कोटलिन है, मैंने सोचा कि मैं नए प्रतिमान के लिए एक और विकल्प जोड़ूंगा। यहां हम विस्तार कार्यों और पुनरीक्षित प्रकारों का उपयोग कर सकते हैं (जो संकलन करते समय प्रकार बरकरार रखता है)।

inline fun <reified T : Enum<T>> Intent.putExtra(victim: T): Intent =
    putExtra(T::class.java.name, victim.ordinal)

inline fun <reified T: Enum<T>> Intent.getEnumExtra(): T? =
    getIntExtra(T::class.java.name, -1)
        .takeUnless { it == -1 }
        ?.let { T::class.java.enumConstants[it] }

इस तरह से करने के कुछ फायदे हैं।

  • हमें क्रमांकन करने के लिए एक मध्यस्थ वस्तु के "ओवरहेड" की आवश्यकता नहीं है क्योंकि यह सब धन्यवाद के स्थान पर किया जाता है inlineजो फ़ंक्शन के अंदर कोड के साथ कॉल को बदल देगा।
  • फ़ंक्शन अधिक परिचित हैं क्योंकि वे एसडीके वाले के समान हैं।
  • आईडीई इन कार्यों को स्वत: पूर्ण करेगा जिसका अर्थ है कि उपयोगिता वर्ग के पिछले ज्ञान की आवश्यकता नहीं है।

डाउनसाइड्स में से एक यह है कि, यदि हम एम्स के क्रम को बदलते हैं, तो कोई भी पुराना संदर्भ काम नहीं करेगा। यह लंबित इरादों के अंदर इरादों जैसी चीजों के साथ एक मुद्दा हो सकता है क्योंकि वे अपडेट से बच सकते हैं। हालांकि, बाकी समय के लिए, यह ठीक होना चाहिए।

यह ध्यान रखना महत्वपूर्ण है कि स्थिति के बजाय नाम का उपयोग करने जैसे अन्य समाधान भी विफल हो जाएंगे यदि हम किसी भी मूल्य का नाम बदलते हैं। हालाँकि, उन मामलों में, हमें गलत Enum मान के बजाय एक अपवाद मिलता है।

उपयोग:

// Sender usage
intent.putExtra(AwesomeEnum.SOMETHING)
// Receiver usage
val result = intent.getEnumExtra<AwesomeEnum>()

14
+1 यह इंगित करने के लिए कि उन्हें व्यापक बनाने के लिए "वास्तविक बुरा विचार" है।
बगिचर

3
मैंने वास्तव में एक ऐसी परियोजना पर काम किया था जहाँ मैं सिर्फ क्रमांकन या बंडलिंग ऑब्जेक्ट्स (बहुत सारे ऑब्जेक्ट्स जिनमें बहुत सारे वैरिएबल होते हैं) से निपटना नहीं चाहता था, और स्थैतिक वैश्विक चर का उपयोग करना ठीक था ... जब तक कि एक टीममेट पर नहीं मिला परियोजना। उन ग्लोबल्स के उपयोग को समन्वित करने की कोशिश की लागत ने मुझे "पेंच कर दिया। मैं कुछ पार्सलबेल बनाने के लिए एक कोड जनरेटर लिख रहा हूं"। कीड़े की संख्या में काफी गिरावट आई
जो प्लांट

2
@ कॉफ़ेक्ट हाँ, यह एक समझने योग्य सुझाव है, लेकिन ज्यादातर मामलों में यह समय से पहले अनुकूलन के रूप में योग्य हो सकता है जब तक कि आप हजारों एनमों को पार्स नहीं कर रहे हैं (जो कि स्वभाव से उन्हें केवल कुछ ही दिए जाने चाहिए जो वे राज्य को संभालने के लिए उपयोग किए जाते हैं) एक Nexus 4 पर आप 1ms सुधार ( developerphil.com/parcelable-vs-serializable ) सुनिश्चित करें कि यह अतिरिक्त पैर के काम के लायक नहीं है, लेकिन फिर आपके पास मेरे द्वारा सुझाए गए अन्य विकल्प हैं;)
pablisco

1
@rgv हुड के तहत कोटलिन क्रॉस enum classएक सादे जावा के प्रकारों को संकलित करता है enum। मुझे लगता है कि enum classलागू करने के लिए आसान समाधान है Serializable: enum class AwesomeEnum : Serializable { A, B, C }आदर्श नहीं है, लेकिन काम करना चाहिए।
pablisco

1
@ किसी भी अच्छे उत्तर के साथ, "यह निर्भर करता है" है। Serialisable को विस्तारित करने की कोई आवश्यकता नहीं है। प्रारंभिक उत्तर मान्य है। उन अतिरिक्त विकल्पों के मामले में है कि आपके पास एक ऐसा मामला है जहां एक बोतल गर्दन हो सकती है, जैसे कि आप लाखों रिकॉर्डों को नष्ट कर रहे हैं (आशा नहीं)। जो आपको फिट दिखाई दे उसका उपयोग करें ...
pablisco

114

आप अपने एनम को लागू कर सकते हैं पार्सल को लागू कर सकते हैं जो एनमों के लिए काफी आसान है:

public enum MyEnum implements Parcelable {
    VALUE;


    @Override
    public int describeContents() {
        return 0;
    }

    @Override
    public void writeToParcel(final Parcel dest, final int flags) {
        dest.writeInt(ordinal());
    }

    public static final Creator<MyEnum> CREATOR = new Creator<MyEnum>() {
        @Override
        public MyEnum createFromParcel(final Parcel source) {
            return MyEnum.values()[source.readInt()];
        }

        @Override
        public MyEnum[] newArray(final int size) {
            return new MyEnum[size];
        }
    };
}

फिर आप Intent.putExtra (स्ट्रिंग, पार्सलेबल) का उपयोग कर सकते हैं।

अद्यतन: कृपया ध्यान दें कि आपके enum.values()कॉल पर एक नया सरणी आवंटित करता है

अद्यतन: एंड्रॉइड स्टूडियो एक लाइव टेम्पलेट पेश करता है ParcelableEnumजो इस समाधान को लागू करता है। (विंडोज पर, उपयोग Ctrl+ J)


3
यह अध्यादेशों के बजाय एनम के इनस्ट्रिंग () और वैल्यूऑफ () के तरीकों से भी संभव है।
नैटिक्स

2
ऑर्डिनल () के उपयोग से विराम हो सकता है, जब डेवलपर नई ईनम सदस्य को सम्मिलित करता है। बेशक, नामांकित सदस्य का नाम बदलने से नाम () भी टूट जाएगा। लेकिन, डेवलपर्स का नाम बदलने के बजाय नए सदस्य को सम्मिलित करने की अधिक संभावना है, क्योंकि नाम बदलने के लिए उसे पूरे प्रोजेक्ट को फिर से कारक बनाना होगा।
चोक यान चेंग

2
मैं इस बात से सहमत नहीं हूं कि नामांकित लोगों की तुलना में अतिरिक्त (या पुनर्व्यवस्थित) एनम मूल्यों की अधिक संभावना है। इंटेलीज आईडीईए रिफैक्टिंग जैसे परिष्कृत आईडीई का उपयोग करना कोई बड़ी बात नहीं है। लेकिन आपकी बात अभी भी अच्छी है: आपको यह सुनिश्चित करना होगा कि क्रमांकन किसी भी सह-अस्तित्व कार्यान्वयन के अनुरूप हो। यह किसी भी प्रकार के क्रमांकन के लिए सही है। मैं मानता हूं कि ज्यादातर मामलों में पार्सल को एक ऐप के आसपास पारित किया जाता है, जहां केवल एक कार्यान्वयन मौजूद होता है, इसलिए यह एक मुद्दा नहीं होना चाहिए।
ओडरिक

2
मान () प्रत्येक कॉल पर एक नया सरणी बनाता है, इसलिए इसे उदा में कैश करना सबसे अच्छा है। एक निजी स्थिर सरणी
wreckgar23

2
यह तथ्य कि सामान्य मामलों में (जैसे डीबी स्टोरेज), ऑर्डिनल () सुरक्षित नहीं है, एंड्रॉइड पार्सल के लिए प्रासंगिक नहीं है। पार्सल लंबे समय तक (लगातार) भंडारण के लिए नहीं होते हैं। वे ऐप के साथ मर जाते हैं। इसलिए जब आप किसी एनम को जोड़ते / नाम बदलते हैं, तो आपको नए पार्सल मिलेंगे।
नोआतम

24

आप एक स्ट्रिंग के रूप में एक एनम पास कर सकते हैं।

public enum CountType {
    ONE,
    TWO,
    THREE
}

private CountType count;
count = ONE;

String countString = count.name();

CountType countToo = CountType.valueOf(countString);

इस बात का समर्थन किया जाता है कि आपको बिना किसी समस्या के आस-पास के मान को पारित करने में सक्षम होना चाहिए।


3
उन सभी का सबसे सरल कार्यान्वयन।
एवी कोहेन

22

इरादे से एक एनम पास करने के लिए, आप एनम को पूर्णांक में बदल सकते हैं।

उदाहरण के लिए:

public enum Num{A ,B}

भेजना (पूर्णांक तक गणना):

Num send = Num.A;
intent.putExtra("TEST", send.ordinal());

प्राप्त करना (एनम के पूर्णांक):

Num rev;
int temp = intent.getIntExtra("TEST", -1);
if(temp >= 0 && temp < Num.values().length)
    rev = Num.values()[temp];

सादर। :)


8
या आप इसे एक स्ट्रिंग के रूप में भेज सकते हैं (ताकि यह पठनीय है) Num.A.name () के साथ और फिर इसे वापस कर लें। Num.ValueOf (इरादे ।getStringExtra ("TEST") का उपयोग करके)
बेनोइट जिंगिन

1
मुझे लगता है कि बेनोइट का रास्ता अधिक सुरक्षित है, क्योंकि अभ्यास में ऑर्डिनल () को प्राथमिकता नहीं दी जाती है क्योंकि ऑर्डिनल () मूल्य बदल सकता है। इस पोस्ट को देखें: stackoverflow.com/questions/2836256/…
Shnkc

15

यदि आपको वास्तव में आवश्यकता है, तो आप एक स्ट्रिंग का उपयोग करते हुए एक एनम को क्रमबद्ध कर सकते हैं name()valueOf(String) , निम्नानुसार और हैं:

 class Example implements Parcelable { 
   public enum Foo { BAR, BAZ }

   public Foo fooValue;

   public void writeToParcel(Parcel dest, int flags) {
      parcel.writeString(fooValue == null ? null : fooValue.name());
   }

   public static final Creator<Example> CREATOR = new Creator<Example>() {
     public Example createFromParcel(Parcel source) {        
       Example e = new Example();
       String s = source.readString(); 
       if (s != null) e.fooValue = Foo.valueOf(s);
       return e;
     }
   }
 }

यह स्पष्ट रूप से काम नहीं करता है यदि आपके एनमों में परिवर्तनशील स्थिति होती है (जो कि उन्हें वास्तव में नहीं चाहिए)।


4

आपके Enum को Serializable कार्यान्वित करना संभव हो सकता है तब आप इसे Intent के माध्यम से पारित कर सकते हैं, क्योंकि इसे Serializable के रूप में पास करने की एक विधि है। एनम के बजाय इंट का उपयोग करने की सलाह फर्जी है। Enums का उपयोग आपके कोड को पढ़ने में आसान और बनाए रखने में आसान बनाने के लिए किया जाता है। यह अंधेरे युग में एक बड़ा कदम होगा जो Enums का उपयोग करने में सक्षम नहीं होगा।


2
कोई भी Enum टाइप Enum सुपरक्लास को डिफ़ॉल्ट रूप से बढ़ाता है, जो पहले से ही Serializable को लागू करता है।
अरकाओ

2

ओदरिक की पोस्ट के बारे में:

आप अपने एनम को लागू कर सकते हैं पार्सल को लागू कर सकते हैं जो एनमों के लिए काफी आसान है:

सार्वजनिक रूप से MyEnum Parcelable को लागू करता है {...} आप Intent.putExtra (स्ट्रिंग, Parcelable) का उपयोग कर सकते हैं।

यदि आप MyEnum चर myEnum को परिभाषित करते हैं, तो इरादे करें ।putExtra ("Parcelable1", myEnum), आपको एक "विधि putExtra (स्ट्रिंग, Parcelable) प्राप्त होगी, जो इरादे प्रकार" त्रुटि संदेश के लिए अस्पष्ट है। चूँकि एक Intent.putExtra (String, Parcelable) विधि भी है, और मूल 'Enum' प्रकार स्वयं Serializable इंटरफ़ेस को लागू करता है, इसलिए कंपाइलर को पता नहीं है कि कौन सी विधि (इरादे ।putExtra (स्ट्रिंग, Parcelable / या Serializable)) है।

सुझाव दें कि MyEnum से पार्सलेबल इंटरफ़ेस को हटा दें, और कोर कोड को रैप क्लास 'पार्सलेबल कार्यान्वयन में स्थानांतरित करें, इस तरह (फादर 2 एक पार्सलेबल है और इसमें एनम फील्ड होता है):

public class Father2 implements Parcelable {

AnotherEnum mAnotherEnum;
int mField;

public Father2(AnotherEnum myEnum, int field) {
    mAnotherEnum = myEnum;
    mField = field;
}

private Father2(Parcel in) {
    mField = in.readInt();
    mAnotherEnum = AnotherEnum.values()[in.readInt()];
}

public static final Parcelable.Creator<Father2> CREATOR = new Parcelable.Creator<Father2>() {

    public Father2 createFromParcel(Parcel in) {
        return new Father2(in);
    }

    @Override
    public Father2[] newArray(int size) {
        return new Father2[size];
    }

};

@Override
public int describeContents() {
    return 0;
}

@Override
public void writeToParcel(Parcel dest, int flags) {
    dest.writeInt(mField);
    dest.writeInt(mAnotherEnum.ordinal());
}

}

तो हम कर सकते हैं:

AnotherEnum anotherEnum = AnotherEnum.Z;
intent.putExtra("Serializable2", AnotherEnum.X);   
intent.putExtra("Parcelable2", new Father2(AnotherEnum.X, 7));

5
आप स्पष्ट रूप से तर्क को "कास्टिंग" करके सही हस्ताक्षर चुन सकते हैं, उदाहरण के लिएintent.putExtra("myEnum", (Parcelable) enumValue);
ओडरिक

ऑर्डिनल का उपयोग करना सही है!
slott

यह कहने का एक बहुत जटिल तरीका है bundle.putExtra("key", AnotherEnum.X.ordinal())
ट्वीस्टेरोब

2

आप ईम प्राइमर का उपयोग कर सकते हैं enum के लिए आदिम डेटा प्रकार है।

public enum DaysOfWeek {
    MONDAY(1),
    TUESDAY(2),
    WEDNESDAY(3),
    THURSDAY(4),
    FRIDAY(5),
    SATURDAY(6),
    SUNDAY(7);

    private int value;
    private DaysOfWeek(int value) {
        this.value = value;
    }

    public int getValue() {
        return this.value;
    }

    private static final SparseArray<DaysOfWeek> map = new SparseArray<DaysOfWeek>();

    static
    {
         for (DaysOfWeek daysOfWeek : DaysOfWeek.values())
              map.put(daysOfWeek.value, daysOfWeek);
    }

    public static DaysOfWeek from(int value) {
        return map.get(value);
    }
}

आप एक्स्ट्रा के रूप में इंट पास करने के लिए उपयोग कर सकते हैं, फिर इसे अपने मूल्य का उपयोग करके एनम से खींच सकते हैं।


2

यहाँ पार्सल योग्य अवधारणा का उपयोग करने वाले अधिकांश उत्तर जावा कोड में हैं। कोटलिन में इसे करना आसान है।

बस @Parcelize और Parcelable इंटरफ़ेस को लागू करने के साथ अपने enum वर्ग को एनोटेट करें ।

@Parcelize
enum class ViewTypes : Parcelable {
TITLE, PRICES, COLORS, SIZES
}

1

मुझे सिंपल पसंद है।

  • फ्रेड गतिविधि के दो मोड हैं - HAPPYऔर SAD
  • एक स्टेटिक बनाएं जो IntentFactoryआपके Intentलिए आपका निर्माण करता है । जो Modeआप चाहते हैं उसे पास करें ।
  • IntentFactoryके नाम का उपयोग करता हैMode अतिरिक्त के नाम के रूप में वर्ग।
  • IntentFactoryधर्मान्तरित Modeएक को Stringउपयोग करते हुएname()
  • onCreateवापस प्रवेश करने के लिए इस जानकारी का उपयोग करने पर प्रवेश करने के लिए Mode
  • आप उपयोग कर सकते हैं ordinal()और Mode.values()साथ ही। मुझे स्ट्रिंग्स पसंद हैं क्योंकि मैं उन्हें डीबगर में देख सकता हूं।

    public class Fred extends Activity {
    
        public static enum Mode {
            HAPPY,
            SAD,
            ;
        }
    
        public void onCreate(Bundle savedInstanceState) {
            super.onCreate(savedInstanceState);
            setContentView(R.layout.betting);
            Intent intent = getIntent();
            Mode mode = Mode.valueOf(getIntent().getStringExtra(Mode.class.getName()));
            Toast.makeText(this, "mode="+mode.toString(), Toast.LENGTH_LONG).show();
        }
    
        public static Intent IntentFactory(Context context, Mode mode){
            Intent intent = new Intent();
            intent.setClass(context,Fred.class);
            intent.putExtra(Mode.class.getName(),mode.name());
    
            return intent;
        }
    }

जिज्ञासु .. इंटेंटफैक्टिंग किसे कहते हैं? क्या आप इस बारे में विस्तार से बता सकते हैं कि कैसे एक अलग गतिविधि फ्रेड को बुलाएगी और फ्रेड कैसे बीमा कर सकता है कि मोड पारित हो गया है?
इरिक

0

मुझे लगता है कि आपकी सबसे अच्छी शर्त उन सूचियों को पार्सल (जैसे मानचित्र) के रूप में कुछ पार्सल में बदलना है, ताकि इसे गतिविधि में लाया जा सके। फिर गतिविधि को इसे एक सरणी में वापस बदलना होगा।

कस्टम पार्सल को लागू करने से गर्दन IMHO में दर्द होता है, इसलिए यदि संभव हो तो मैं इसे टाल दूंगा।


0

निम्नलिखित enum पर विचार करें ::

public static  enum MyEnum {
    ValueA,
    ValueB
}

पासिंग के लिए ::

 Intent mainIntent = new Intent(this,MyActivity.class);
 mainIntent.putExtra("ENUM_CONST", MyEnum.ValueA);
 this.startActivity(mainIntent);

आशय / बंडल / तर्क से वापस पाने के लिए ::

 MyEnum myEnum = (MyEnum) intent.getSerializableExtra("ENUM_CONST");

0

यदि आप सिर्फ एक एनम भेजना चाहते हैं तो आप कुछ ऐसा कर सकते हैं:

पहले कुछ मूल्य युक्त एक एनम घोषित करें (जिसे इरादे से पारित किया जा सकता है):

 public enum MyEnum {
    ENUM_ZERO(0),
    ENUM_ONE(1),
    ENUM_TWO(2),
    ENUM_THREE(3);
    private int intValue;

    MyEnum(int intValue) {
        this.intValue = intValue;
    }

    public int getIntValue() {
        return intValue;
    }

    public static MyEnum getEnumByValue(int intValue) {
        switch (intValue) {
            case 0:
                return ENUM_ZERO;
            case 1:
                return ENUM_ONE;
            case 2:
                return ENUM_TWO;
            case 3:
                return ENUM_THREE;
            default:
                return null;
        }
    }
}

फिर:

  intent.putExtra("EnumValue", MyEnum.ENUM_THREE.getIntValue());

और जब आप इसे प्राप्त करना चाहते हैं:

  NotificationController.MyEnum myEnum = NotificationController.MyEnum.getEnumByValue(intent.getIntExtra("EnumValue",-1);

केक का टुकड़ा!


0

कोटलिन एक्सटेंशन फ़ंक्शंस का उपयोग करें

inline fun <reified T : Enum<T>> Intent.putExtra(enumVal: T, key: String? = T::class.qualifiedName): Intent =
    putExtra(key, enumVal.ordinal)

inline fun <reified T: Enum<T>> Intent.getEnumExtra(key: String? = T::class.qualifiedName): T? =
    getIntExtra(key, -1)
        .takeUnless { it == -1 }
        ?.let { T::class.java.enumConstants[it] }

यह आपको एक ही एनम प्रकार के कई पास करने के लिए लचीलापन देता है, या वर्ग नाम का उपयोग करने के लिए डिफ़ॉल्ट है।

// Add to gradle
implementation "org.jetbrains.kotlin:kotlin-reflect:$kotlin_version"

// Import the extension functions
import path.to.my.kotlin.script.putExtra
import path.to.my.kotlin.script.getEnumExtra

// To Send
intent.putExtra(MyEnumClass.VALUE)

// To Receive
val result = intent.getEnumExtra<MyEnumClass>()

-2

Enums का उपयोग न करें। Enums का उपयोग नहीं करने के लिए कारण # 78। :) पूर्णांक का उपयोग करें, जिसे आसानी से बंडल और पार्सल के माध्यम से प्रेषित किया जा सकता है।


8
@hackbod - अन्य 77 कारण क्या हैं? ;) गंभीरता से हालांकि - लगता है कि लाभ के लिए कई फायदे हैं और वे 'दूरस्थ' के लिए बिल्कुल मुश्किल नहीं हैं - कोई भी मौका जो आप उनके खिलाफ अपने कारणों पर विस्तार कर सकते हैं?
ostergaard

3
@hackbod कृपया विस्तृत करें। अगर एनम का उपयोग नहीं किया जाना चाहिए, तो उन्हें एपीआई से हटा दें।
dcow

2
एनम जावा भाषा विनिर्देश का हिस्सा हैं, इसलिए उन्हें हटाने के लिए थोड़ा कठिन है और अभी भी एक अनुपालन जावा कार्यान्वयन है :)
tad

1
किस बारे में mEnum.ordinal()? यह तत्व की स्थिति लौटाता है
सैफ हमीद

3
का मूल्य Enum.ordinal()संकलन समय पर निर्धारित किया जाता है। केवल उस समय जो टिप्पणी लागू होती है , वह एनम के विभिन्न संस्करणों के साथ ऐप्स के बीच डेटा को पारित करने या ऐप अपडेट के दौरान होगी जो एनम के भीतर तत्वों के क्रम को बदलते हैं। जब भी आप ऐसी किसी भी चीज का उपयोग करते हैं तो वह खतरनाक होती है। एक ही ऐप के भीतर गतिविधियों के बीच इंटेंट पास करने के लिए, Enum.ordinal()पूरी तरह से सुरक्षित होना चाहिए।
इयान मैक्लेयर
हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.