একটি উদ্দেশ্য দ্বারা enum বা অবজেক্ট পাস (সেরা সমাধান)


221

আমার একটি ক্রিয়াকলাপ রয়েছে যা শুরু হওয়ার পরে দুটি পৃথক অ্যারেলিস্টে অ্যাক্সেস দরকার। উভয় তালিকাগুলি আমি নিজে তৈরি করেছি different

মূলত আমার কোনও উদ্দেশ্য থেকে ক্রিয়াকলাপে এই জিনিসগুলি পাস করার একটি উপায় প্রয়োজন। আমি অ্যাডেক্সট্রা () ব্যবহার করতে পারি তবে এর জন্য পার্সেবল সামঞ্জস্যপূর্ণ বর্গ প্রয়োজন। আমি আমার ক্লাসগুলি সিরিয়ালিয়াল পাস করার জন্য তৈরি করতে পারতাম তবে আমি বুঝতে পারছি যে এটি প্রোগ্রামটি ধীর করে দেয়।

আমার বিকল্পগুলি কি?

আমি কি একটি এনুম পাস করতে পারি?

অন্যদিকে যেমন: কোনও উদ্বেগের কাছ থেকে ক্রিয়াকলাপের জন্য প্যারামিটারগুলি পাস করার কোনও উপায় আছে কি?


হতে পারে আমি কিছু মিস করছি, তবে একটি এনাম কীভাবে অ্যারেলিস্টের সাথে সম্পর্কিত?
মার্টিন কনেকেনি

উত্তর:


558

এটি একটি পুরানো প্রশ্ন, তবে প্রত্যেকে এনামস আসলেই উল্লেখ করতে ব্যর্থ হয় Serializableএবং তাই কোনও অতিরিক্ত হিসাবে ইন্টেন্টে পুরোপুরি যুক্ত করা যায়। এটার মত:

public enum AwesomeEnum {
  SOMETHING, OTHER;
}

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

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

স্ট্যাটিক বা অ্যাপ্লিকেশন-বিস্তৃত ভেরিয়েবলগুলি ব্যবহার করার পরামর্শটি একটি সত্যই খারাপ ধারণা। এটি সত্যই আপনার রাজ্য পরিচালনা ব্যবস্থাতে আপনার ক্রিয়াকলাপগুলিকে জুড়ে দেয় এবং এটি বজায় রাখা, ডিবাগ করা এবং সমস্যাবদ্ধ হওয়া শক্ত।


বিকল্প:

টেডিজ্যাকের দ্বারা ওডেরিকের প্রদত্ত সমাধানটি আপনাকে একটি ত্রুটি দেয় বলে একটি ভাল বিষয় উল্লেখ করা হয়েছিল । তবে দেওয়া বিকল্পটি ব্যবহার করার জন্য কিছুটা জটিল (এমনকি জেনেরিকগুলি ব্যবহার করে)।

যদি আপনি সত্যিই কোনও উদ্বেগের সাথে এনাম যুক্ত করার পারফরম্যান্স সম্পর্কে উদ্বিগ্ন হন তবে আমি পরিবর্তিত এই বিকল্পগুলির প্রস্তাব করছি:

বিকল্প 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: (জেনেরিক, পুনরায় ব্যবহারযোগ্য এবং এনাম থেকে 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যার জন্য ফাংশনের অভ্যন্তরের কোডের সাথে কলগুলি প্রতিস্থাপন করবে thanks
  • ফাংশনগুলি আরও পরিচিত কারণ তারা এসডিকে অনুরূপ।
  • আইডিই এই ফাংশনগুলি স্বতঃপূরণ করবে যার অর্থ ইউটিলিটি শ্রেণীর পূর্বের জ্ঞান থাকা দরকার নেই।

ডাউনসাইডগুলির মধ্যে একটি হ'ল, আমরা যদি ইমদের ক্রমটি পরিবর্তন করি তবে কোনও পুরানো রেফারেন্স কাজ করবে না। এটি মুলতুবি থাকা ইন্টেন্টের অভ্যন্তরে অন্তর্ভুক্ত জাতীয় জিনিসগুলির সাথে সমস্যা হতে পারে কারণ তারা আপডেটগুলি টিকে থাকতে পারে। তবে, বাকি সময়ের জন্য, এটি ঠিক থাকা উচিত।

এটি উল্লেখ করা গুরুত্বপূর্ণ যে অন্যান্য সমাধানগুলি যেমন অবস্থানের পরিবর্তে নাম ব্যবহার করাও ব্যর্থ হবে যদি আমরা কোনও মানটির নাম পরিবর্তন করি। যদিও, এই ক্ষেত্রে, আমরা ভুল এনাম মানের পরিবর্তে একটি ব্যতিক্রম পাই।

ব্যবহার:

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

14
তাদের অ্যাপ্লিকেশনকে প্রশস্ত করার জন্য এটি একটি "সত্যিকারের খারাপ ধারণা" ting
বাগফিক্সার

3
আমি আসলে এমন একটি প্রকল্পে কাজ করেছি যেখানে আমি কেবল সিরিয়ালাইজেশন বা বান্ডিলিং অবজেক্ট (প্রচুর পরিমাণে ভেরিয়েবল সহ অনেকগুলি বস্তু) নিয়ে কাজ করতে চাইনি, এবং স্থির গ্লোবাল ভেরিয়েবলগুলি ব্যবহার করা ভাল ছিল ... যতক্ষণ না কোনও সতীর্থ তার দিকে না যায় প্রকল্পের। এই গ্লোবালগুলির ব্যবহারের সমন্বয় করার চেষ্টা করার ব্যয় আমাকে "এটিকে স্ক্রু করতে বাধ্য করল I'm বাগের সংখ্যা উল্লেখযোগ্যভাবে হ্রাস পেয়েছে
জো প্লান্ট

2
@ কাইফ্যাক্ট হ্যাঁ, এটি একটি বোধগম্য পরামর্শ, তবে বেশিরভাগ ক্ষেত্রে এটি অকালীন অপ্টিমাইজেশন হিসাবে যোগ্য হতে পারে যদি না আপনি হাজার হাজার এনামকে পার্স না করেন (যা প্রকৃতির দ্বারা তারা রাষ্ট্র পরিচালনার জন্য ব্যবহার করা হয় তবে কয়েকটি মাত্র হওয়া উচিত) একটি নেক্সাস 4 এ আপনি 1 মিমি উন্নতি পেয়েছেন ( বিকাশকারী
প্যারস্লেবল-vs

1
@rgv হুডের নিচে কোটলিন ক্রস enum classএকটি সরল জাভাতে টাইপ করে enum। আমার ধারণা, enum classবাস্তবায়নটি সহজতর কাজ Serializable: enum class AwesomeEnum : Serializable { A, B, C }আদর্শ নয়, তবে কাজ করা উচিত।
পাব্লিসকো

1
@ পিয়ারে যে কোনও ভাল উত্তরের মতো একটি "এটি নির্ভর করে" আছে। সিরিয়ালিসেবল বাড়ানোর দরকার নেই। প্রাথমিক উত্তরটি বৈধ। এই অতিরিক্ত বিকল্পগুলির ক্ষেত্রে আপনার বোতল ঘাড় থাকতে পারে এমন একটি মামলা রয়েছে যেমন আপনি কয়েক মিলিয়ন রেকর্ডকে deserialise করছেন (আশা করি না)। আপনি যা দেখতে ফিট তা ব্যবহার করুন ...
পাব্লিসকো

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];
        }
    };
}

তারপরে আপনি ইনটেন্ট.পুটেক্সট্রা (স্ট্রিং, পার্সেবল) ব্যবহার করতে পারেন।

আপডেট: দয়া করে রেকারারের মন্তব্যটি নোট করুন যা enum.values()প্রতিটি কলে একটি নতুন অ্যারে বরাদ্দ করে।

আপডেট: অ্যান্ড্রয়েড স্টুডিওতে একটি লাইভ টেম্পলেট রয়েছে ParcelableEnumযা এই সমাধানটি কার্যকর করে । (উইন্ডোজে, Ctrl+ ব্যবহার করুন J)


3
এটি অর্ডিনালের পরিবর্তে এনামের টসস্ট্রিং () এবং মান ওফ () পদ্ধতিগুলিও সম্ভব।
ন্যাটিক্স

2
অর্ডিনাল () ব্যবহার করে ভাঙ্গতে পারে, যখন ডেভেলপাররা নতুন এনাম সদস্য .ুকিয়ে দেয়। অবশ্যই এনাম সদস্যের নাম পরিবর্তন করলে নামও ভেঙে যায়) তবে, বিকাশকারীরা নতুন নামকরণের পরিবর্তে নতুন সদস্য সন্নিবেশ করানোর সম্ভাবনা বেশি থাকে, কারণ নাম পরিবর্তনের জন্য পুরো প্রকল্পটি পুনরায় ফ্যাক্টর করা প্রয়োজন।
চেওক ইয়ান চেং

2
আমি সম্মত নই যে নামকরণের পরিবর্তে অতিরিক্ত (বা পুনঃক্রম করা) এনাম মানগুলি সম্ভবত বেশি হয়। ইন্টেলিজ আইডিইএ রিফ্যাক্টরিংয়ের মতো একটি পরিশীলিত আইডিই ব্যবহার করা কোনও বড় বিষয় নয়। তবে আপনার বক্তব্যটি এখনও ভাল: আপনার অবশ্যই নিশ্চিত করতে হবে যে কোনওরকম সহাবস্থান বাস্তবায়নের সময় সিরিয়ালটি ধারাবাহিক। এটি কোনও ধরণের সিরিয়ালাইজেশনের ক্ষেত্রে সত্য। আমি অনুমান করি বেশিরভাগ ক্ষেত্রে পার্সেবলগুলি এমন এক অ্যাপের চারপাশে পাস করা হয় যেখানে কেবলমাত্র একটি বাস্তবায়ন বিদ্যমান, যাতে এটি কোনও সমস্যা না হয়।
ওডেরিক

2
মান () প্রতিটি কলটিতে একটি নতুন অ্যারে তৈরি করে, তাই এটি উদাহরণস্বরূপ ক্যাশে করা ভাল। একটি ব্যক্তিগত স্ট্যাটিক অ্যারে
wreckgar23

2
সাধারণ ক্ষেত্রে (যেমন ডিবি স্টোরেজ), অর্ডিনাল () নিরাপদ নয় এ বিষয়টি Android পার্সেলের ক্ষেত্রে প্রাসঙ্গিক নয়। পার্সেলগুলি দীর্ঘমেয়াদী (অবিরাম) স্টোরেজের জন্য নয়। তারা অ্যাপ দিয়ে মারা যায়। সুতরাং আপনি যখন একটি এনাম যুক্ত / নামকরণ করবেন, আপনি নতুন পার্সেল পাবেন get
নভেম্বর

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 (intent.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

আপনার এনামকে সিরিয়ালাইজেবল বাস্তবায়িত করা সম্ভব হতে পারে তবে আপনি এটিকে ইন্টেন্টের মাধ্যমে পাস করতে পারবেন, কারণ এটি সিরিয়ালীকরণযোগ্য হিসাবে পাস করার জন্য একটি পদ্ধতি রয়েছে। এনামের পরিবর্তে ইন্ট ব্যবহারের পরামর্শটি হ'ল বোগাস। আপনার কোডগুলি পড়া সহজ এবং বজায় রাখা সহজ করার জন্য এনামগুলি ব্যবহার করা হয়। এনামগুলি ব্যবহার করতে সক্ষম না হওয়ায় এটি অন্ধকার যুগের পিছনে একটি বড় পদক্ষেপ।


2
কোনও এনুম টাইপ এনাম সুপারক্লাসকে ডিফল্টরূপে প্রসারিত করে, যা ইতিমধ্যে সিরিয়ালাইজেবল প্রয়োগ করে।
আরকাও

2

ওডেরিকের পোস্ট সম্পর্কে:

আপনি আপনার এনামকে পার্সেবল কার্যকর করতে পারেন যা এনামগুলির পক্ষে যথেষ্ট সহজ:

পাবলিক এনাম মাইনেম পার্সেলেবল প্রয়োগ করে {...} আপনি ইনটেন্ট.পুটেক্সট্রা (স্ট্রিং, পার্সেবল) ব্যবহার করতে পারেন।

যদি আপনি একটি মাইনেম পরিবর্তনশীল মাইএনম সংজ্ঞায়িত করেন, তবে ইন্টেন্ট.পুটেক্সট্রা ("পার্সেলেবল 1", মাইইনাম) করুন, আপনি একটি "মেথড পুটেক্সট্রা (স্ট্রিং, পার্সেবল) টাইপ ইন্টেন্ট" ত্রুটি বার্তাটির জন্য অস্পষ্ট। কারণ সেখানে একটি ইন্টেন্ট.পুটেক্সট্রা (স্ট্রিং, পার্সেবল) পদ্ধতিও রয়েছে এবং মূল 'এনুম' টাইপ নিজেই সিরিয়ালাইজেবল ইন্টারফেস প্রয়োগ করে, তাই সংকলক জানেন না কোন পদ্ধতিটি বেছে নিন (ইন্টেন্ট.পুটেক্সট্রা (স্ট্রিং, পার্সেবল / বা সিরিয়ালাইজযোগ্য))।

প্রস্তাব করুন যে মাইএনম থেকে পার্সেবল ইন্টারফেসটি সরিয়ে ফেলুন এবং কোর কোডটি মোড়কের শ্রেণিতে 'পার্সেবল ইমপ্লিমেশন'-এ স্থানান্তর করুন, এর মতো (ফাদার 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);
ingালাই

অর্ডিনাল ব্যবহার নিখুঁত!
স্লোট

এটি বলার সত্যিই জটিল উপায় bundle.putExtra("key", AnotherEnum.X.ordinal())
TWiStErRob

2

আপনি প্রাথমিক তথ্য টাইপ করতে এনামের জন্য এনাম কনস্ট্রাক্টর ব্যবহার করতে পারেন ..

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

পার্সেবল ধারণাটি এখানে ব্যবহার করা বেশিরভাগ উত্তর জাভা কোডে। কোটলিনে এটি করা সহজ।

শুধু সঙ্গে আপনার enum বর্গ টীকা @Parcelize এবং Parcelable ইন্টারফেস বাস্তবায়ন।

@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

নিম্নলিখিত এনাম ::

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

এনাম ব্যবহার করবেন না। এনামগুলি ব্যবহার না করার কারণ # 78। :) পূর্ণসংখ্যার ব্যবহার করুন, যা বান্ডেল এবং পার্সেবলের মাধ্যমে সহজেই সরিয়ে নেওয়া যায়।


8
@ হ্যাকবড - অন্যান্য 77 77 টি কারণ কী? ;) গুরুতরভাবে যদিও - এনামের অনেক সুবিধা রয়েছে বলে মনে হয় এবং এগুলি 'রিমোট' করা ঠিক তেমন কঠিন নয় - কোনও কারণেই যদি আপনি তাদের বিরুদ্ধে আপনার কারণগুলি প্রসারিত করতে পারেন?
অস্টেরগার্ড

3
@ হ্যাকবড দয়া করে বিস্তারিত বলুন। যদি এনামগুলি ব্যবহার না করা থাকে তবে এগুলি এপিআই থেকে সরান।
ডিসকো

2
তাই তারা মুছে ফেলুন এবং এখনও একটি অনুবর্তী জাভা বাস্তবায়ন :) আছে একটু শক্ত করছি Enums, জাভা ভাষা স্পেসিফিকেশন অংশ
বাচ্চা

1
কি mEnum.ordinal()? এটি উপাদানটির অবস্থানটি ফিরিয়ে দেয়
সাইফ হামেদ

3
Enum.ordinal()সংকলনের সময়টির মান নির্ধারিত হয়। মন্তব্যটি প্রয়োগ করার সময়টি কেবলমাত্র মধ্যবর্তী ডেটা হ'ল অ্যাপ্লিকেশান enum বিভিন্ন সংস্করণ সঙ্গে, বা যে enum মধ্যে উপাদানগুলি ক্রম পরিবর্তন অ্যাপ্লিকেশনের আপডেটগুলি জুড়ে। আপনি যখন আদিম নয় এমন কিছু ব্যবহার করেন তখন এই ধরণের জিনিসটি বিপজ্জনক। একটি একক অ্যাপ্লিকেশনের মধ্যে ক্রিয়াকলাপগুলির মধ্যে উদ্দেশ্যগুলি পাস করার জন্য, Enum.ordinal()সম্পূর্ণ নিরাপদ হওয়া উচিত be
ইয়ান ম্যাকলেয়ার্ড
আমাদের সাইট ব্যবহার করে, আপনি স্বীকার করেছেন যে আপনি আমাদের কুকি নীতি এবং গোপনীয়তা নীতিটি পড়েছেন এবং বুঝতে পেরেছেন ।
Licensed under cc by-sa 3.0 with attribution required.