নতুন তালিকা তৈরি না করে তালিকায় সেট রূপান্তর করুন


503

আমি একটি রূপান্তর করার জন্য এই কোড ব্যবহার করছি Setএকটি থেকে List:

Map<String, List<String>> mainMap = new HashMap<>();

for (int i=0; i < something.size(); i++) {
  Set<String> set = getSet(...); //returns different result each time
  List<String> listOfNames = new ArrayList<>(set);
  mainMap.put(differentKeyName, listOfNames);
}

আমি লুপের প্রতিটি পুনরাবৃত্তিতে একটি নতুন তালিকা তৈরি করা এড়াতে চাই। এটা কি সম্ভব?


1
আমি কিউ হিসাবে সেট তালিকায় রূপান্তর করার একটি উপায় জানি I প্রতিবার লুপে নতুন তালিকা তৈরি করা এড়াতে চাই।
মুহাম্মদ ইমরান তারিক

4
আপনি কেন কেবল মূল তালিকাতে সেট যুক্ত করতে পারবেন না? আপনার কেন সেটকে তালিকায় রূপান্তর করতে হবে?
DagR

1
আপনার তালিকা <তালিকা <? >>
হাইরি নমস

5
আপনি পারবেন না। আপনার প্রশ্নটি পদগুলিতে একটি বৈপরীত্যের সূচনা করে।
লার্নের মারকুইস

উত্তর:


802

আপনি List.addAll () পদ্ধতিটি ব্যবহার করতে পারেন । এটি একটি সংগ্রহকে আর্গুমেন্ট হিসাবে গ্রহণ করে এবং আপনার সেটটি সংগ্রহ।

List<String> mainList = new ArrayList<String>();
mainList.addAll(set);

সম্পাদনা: প্রশ্নের সম্পাদনা হিসাবে প্রতিক্রিয়া।
এটি দেখতে সহজ যে আপনি যদি মানগুলির Mapসাথে একটি Listমান রাখতে চান তবে k এর বিভিন্ন মান থাকতে হলে আপনাকে k এর বিভিন্ন তালিকা তৈরি করতে হবে।
সুতরাং: আপনি এই তালিকা তৈরি করা একেবারেই এড়াতে পারবেন না, তালিকা তৈরি করতে হবে।

আশেপাশের সম্ভাব্য কাজ: এটিকে বা তার পরিবর্তে
ঘোষণা করুন এবং কেবল আপনার সেটটি সন্নিবেশ করুন।MapMap<String,Set>Map<String,Collection>


1
দুঃখিত এটি মূল তালিকা ছিল না তালিকা। প্রশ্ন দেখুন
মুহাম্মদ ইমরান তারিক

@ আইমরান্ট্রিক: differentKeyNameপ্রতিটি পুনরাবৃত্তি পরিবর্তন হচ্ছে ? আপনি কি something.size()আপনার মানচিত্রে ভিন্ন ভিন্ন সম্ভাব্য মান চান ? এটি দেখতে সহজ যে kতালিকা হিসাবে মানচিত্রের মানচিত্রে কমপক্ষে kতালিকা তৈরি করা দরকার create
amit

@ আইমরান্ট্রিক: এবং আমি ধরে নিয়েছি প্রতিটি কীগুলির জন্য আপনি আলাদা তালিকা চান?
amit

@ আইমরান্টরিক: আপনি যা অনুরোধ করছেন তা অসম্ভব। আরও তথ্যের জন্য আমার সম্পাদনা পড়ুন।
amit

সেটটি যদি নাল হয় তবে এটি নালপয়েন্টারএক্সসেপশন ফিরিয়ে দেবে।
w35l3y

411

এটি রূপান্তর করতে কনস্ট্রাক্টর ব্যবহার করুন:

List<?> list = new ArrayList<?>(set);

21
তিনি স্পষ্টতই বলেছিলেন যে তিনি এড়াতে চান।
mapeters

3
@ ইমাক অপ্রাসঙ্গিক, কারণ তার প্রয়োজনীয়তা প্রয়োগযোগ্য নয়।
লার্নের মারকুইস

16
@ এজেপি তখন তার উত্তরটি বলা দরকার, ওপিকে কোনও ব্যাখ্যা না দিয়ে কিছু বলার পরিবর্তে।
পরিসংখ্যানকারীরা

তিনি এড়িয়ে চলেছেন, কনস্ট্রাক্টর System.arrayCopy ব্যবহার করে, যা অগভীর অনুলিপি তৈরি করে, অর্থাত্, এটি কেবলমাত্র তালিকা তৈরির জন্য ব্যবহৃত অ্যারেতে অবজেক্টগুলির রেফারেন্সগুলি অনুলিপি করে। আপনি যদি উভয় সংগ্রহের তুলনা করেন, আপনি দেখতে পাবেন যে এগুলি উভয়ই একই অবজেক্টের রেফারেন্স রয়েছে।
গুব্যাট্রন

এটি আসলে অ্যান্ড্রয়েডে কাজ করে না। কোন কারণে কেন?
Kbluue

84

এছাড়াও পেয়ারা সংগ্রহ লাইব্রেরি থেকে আপনি ব্যবহার করতে পারেন newArrayList(Collection):

Lists.newArrayList([your_set])

এটি অ্যামিটের পূর্বের উত্তরের সাথে সমান হবে , আপনি কোনও listবস্তু ঘোষণার (বা তাত্ক্ষণিক) প্রয়োজন হবে না ।


1
আপনি যদি পেয়ারা ব্যবহার করছেন তবে এটি কার্যকর
vsingh

6
যদিও আপনি সরাসরি কনস্ট্রাক্টরকে কল দিচ্ছেন না, এই পদ্ধতিটি এখনও ArrayListকনস্ট্রাক্টরকে কল করে ।
glen3b

আমি যদি কোনও তালিকা ঘোষণা না করি তবে কীভাবে তৈরি তালিকাটি ব্যবহার করতে পারি?
Koray Tugay

@ কোরেটগুয়ে, ভাল আপনি ভেরিয়েবলের (স্থানীয় বা বিশ্বব্যাপী) তালিকাগুলি.নেউআরআরলিস্ট ([আপনার_সেট]) নিষ্কাশন করুন । উদাহরণস্বরূপ: <Foo> fooList = list.newArrayList (setOfFoo) তালিকা করুন তবে আপনার প্রশ্নটি ত্রুটিযুক্ত। আপনি যদি একটি তালিকা তৈরি করেন তবে এটি অন্তত অন্তর্নিহিতভাবে ঘোষণা করা হয়েছে (যদি স্পষ্টভাবে না হয়)।
ছাইয়াছাইয়া

1
কেন এই পদ্ধতিটি তৈরি হয়েছিল তা সম্পর্কে কোনও ধারণা? এর চেয়ে ভাল আর মনে হয় না new ArrayList<>([your_set])
ডেভিডএস

48

আমরা জাভা 8 এ নিম্নলিখিত একটি লাইনার ব্যবহার করতে পারি:

List<String> list = set.stream().collect(Collectors.toList());

এখানে একটি ছোট উদাহরণ:

public static void main(String[] args) {
        Set<String> set = new TreeSet<>();
        set.add("A");
        set.add("B");
        set.add("C");
        List<String> list = set.stream().collect(Collectors.toList());
}

7
পাঠযোগ্যতার জন্য এটি প্রস্তাবিত নয়। উদাহরণস্বরূপ, ইন্টেলিজি "নতুন অ্যারেলিস্ট <> (সেট)" পরামর্শ দেয় এবং 20 টিরও বেশি অনুরূপ কোডের নমুনাগুলি তালিকাভুক্ত করে একইভাবে প্রতিস্থাপন করা যায়।
rrhrg

ঠিক! @rrrrrg যদি আমরা set.parallelStream () ব্যবহার করি তবে পারফরম্যান্সের পক্ষে আরও ভাল?
গৌরব

31

সহজ সমাধান

আমি আমার সেটটিকে তালিকায় রূপান্তর করতে এবং এটি ফিরিয়ে দিতে খুব দ্রুত উপায় চেয়েছিলাম, তাই এক লাইনে করেছিলাম

 return new ArrayList<Long>(mySetVariable);

1
এটি হ'ল এপিআই প্রবাহের পরিবর্তে ইন্টেলিজ আইডিইএ পরামর্শ দেয়।
বেন

6

আপনি এই এক লাইন পরিবর্তনটি ব্যবহার করতে পারেন: Arrays.asList(set.toArray(new Object[set.size()]))

Map<String, List> mainMap = new HashMap<String, List>();

for(int i=0; i<something.size(); i++){
  Set set = getSet(...); 
  mainMap.put(differentKeyName, Arrays.asList(set.toArray(new Object[set.size()])));
}  

আকারটি সংশোধন করা হয়েছে কারণ নতুন অবজেক্ট [0] কেবল একটি উপাদান রাখবে তবে নতুন অবজেক্ট [set.size ()] সব মান ধরে রাখবে
rajadilipkolli

5

আমি করবো :

Map<String, Collection> mainMap = new HashMap<String, Collection>();

for(int i=0; i<something.size(); i++){
  Set set = getSet(...); //return different result each time
  mainMap.put(differentKeyName,set);
}

4

যেহেতু এটি এখনও অবধি উল্লেখ করা হয়নি, তাই জাভা 10 হিসাবে আপনি নতুন copyOfকারখানার পদ্ধতিটি ব্যবহার করতে পারেন :

List.copyOf(set);

জাভাডোক থেকে :

প্রদত্ত সংগ্রহের উপাদানগুলিকে এর পুনরাবৃত্তির ক্রম অনুসারে একটি অবিরাম পরিবর্তনযোগ্য তালিকা প্রদান করে।


3

জাভা 8 স্ট্রিমগুলি ব্যবহারের বিকল্প সরবরাহ করে এবং আপনি এটি থেকে একটি তালিকা পেতে পারেন Set<String> setString:

List<String> stringList = setString.stream().collect(Collectors.toList());

যদিও এখন পর্যন্ত অভ্যন্তরীণ বাস্তবায়ন এর উদাহরণ দেয় ArrayList:

public static <T>
    Collector<T, ?, List<T>> toList() {
        return new CollectorImpl<>((Supplier<List<T>>) ArrayList::new, List::add,
                                   (left, right) -> { left.addAll(right); return left; },
                                   CH_ID);
    }

তবে জেডিকে এর গ্যারান্টি দেয় না। যেমনটি এখানে উল্লেখ করা হয়েছে :

তালিকার ধরণ, পরিবর্তনীয়তা, ধারাবাহিকতা বা থ্রেড-সুরক্ষার কোনও গ্যারান্টি নেই; যদি প্রত্যাবর্তিত তালিকার উপর আরও নিয়ন্ত্রণের প্রয়োজন হয়, সারণি (সরবরাহকারী) ব্যবহার করুন।

আপনি যদি সর্বদা নিশ্চিত হতে চান তবে আপনি উদাহরণ হিসাবে বিশেষত অনুরোধ করতে পারেন:

List<String> stringArrayList = setString.stream()
                     .collect(Collectors.toCollection(ArrayList::new));

2

আমি সহজ staticপদ্ধতি তৈরি করি :

public static <U> List<U> convertSetToList(Set<U> set)
{
    return new ArrayList<U>(set);
}

... বা আপনি যদি তালিকার প্রকার সেট করতে চান তবে আপনি ব্যবহার করতে পারেন:

public static <U, L extends List<U>> List<U> convertSetToList(Set<U> set, Class<L> clazz) throws InstantiationException, IllegalAccessException
{
    L list = clazz.newInstance();
    list.addAll(set);
    return list;
}

2

সম্প্রতি আমি এটি খুঁজে পেয়েছি:

ArrayList<T> yourList = Collections.list(Collections.enumeration(yourSet<T>));

1
আপনি কি এ সম্পর্কে আরও প্রসারিত বা বিস্তৃত করতে পারেন?
ভ্যান্ডেল

সংগ্রহগুলি.লিস্ট () একটি নতুন public static <T> ArrayList<T> list(Enumeration<T> e) { ArrayList<T> l = new ArrayList<>(); while (e.hasMoreElements()) l.add(e.nextElement()); return l; }
অ্যারেলিস্ট

2

শেষ করার জন্য...

আপনি বলে দিন সত্যিই কি আচরণ করতে চান Mapযেমন মান Listগুলি, কিন্তু আপনি অনুলিপি এড়াতে চান Setএকটি মধ্যে Listপ্রতিটি সময়।

উদাহরণ হিসেবে বলা যায়, আপনি হয়ত একটি সৃষ্টি এক লাইব্রেরি ফাংশন আহ্বান করা হয় Set, কিন্তু আপনি আপনার ক্ষণস্থায়ী হয় Map<String, List<String>>একটি (দুর্বল ডিজাইন কিন্তু আপনার হাত থেকে) গ্রন্থাগারের ফাংশন যা শুধুমাত্র লাগে ফলাফলের Map<String, List<String>>যদিও একরকম আপনি কি জানেন যে অপারেশন এটা দিয়ে কাজ করে Listগুলি যে কোনও Collection(এবং এইভাবে কোনও Set) ক্ষেত্রে সমানভাবে প্রযোজ্য । এবং কোনও কারণে আপনাকে প্রতিটি সেটকে একটি তালিকায় অনুলিপি করার গতি / মেমরির ওভারহেড এড়াতে হবে।

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

আপনি এমন একটি শ্রেণি তৈরি করতে চান যা Listইন্টারফেস প্রয়োগ করে , Setকনস্ট্রাক্টারে নিয়ে যায় এবং ক্ষেত্রের জন্য সেট করে দেয় এবং তারপরে এপিআই Setপ্রয়োগ করতে List( অভ্যন্তরীণ পরিমাণ এবং পছন্দসই) প্রয়োগ করে ।

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

public class ListViewOfSet<U> implements List<U> {
    private final Set<U> wrappedSet;
    public ListViewOfSet(Set<U> setToWrap) { this.wrappedSet = setToWrap; }

    @Override public int size() { return this.wrappedSet.size(); }
    @Override public boolean isEmpty() { return this.wrappedSet.isEmpty(); }
    @Override public boolean contains(Object o) { return this.wrappedSet.contains(o); }
    @Override public java.util.Iterator<U> iterator() { return this.wrappedSet.iterator(); }
    @Override public Object[] toArray() { return this.wrappedSet.toArray(); }
    @Override public <T> T[] toArray(T[] ts) { return this.wrappedSet.toArray(ts); }
    @Override public boolean add(U e) { return this.wrappedSet.add(e); }
    @Override public boolean remove(Object o) { return this.wrappedSet.remove(o); }
    @Override public boolean containsAll(Collection<?> clctn) { return this.wrappedSet.containsAll(clctn); }
    @Override public boolean addAll(Collection<? extends U> clctn) { return this.wrappedSet.addAll(clctn); }
    @Override public boolean addAll(int i, Collection<? extends U> clctn) { throw new UnsupportedOperationException(); }
    @Override public boolean removeAll(Collection<?> clctn) { return this.wrappedSet.removeAll(clctn); }
    @Override public boolean retainAll(Collection<?> clctn) { return this.wrappedSet.retainAll(clctn); }
    @Override public void clear() { this.wrappedSet.clear(); }
    @Override public U get(int i) { throw new UnsupportedOperationException(); }
    @Override public U set(int i, U e) { throw new UnsupportedOperationException(); }
    @Override public void add(int i, U e) { throw new UnsupportedOperationException(); }
    @Override public U remove(int i) { throw new UnsupportedOperationException(); }
    @Override public int indexOf(Object o) { throw new UnsupportedOperationException(); }
    @Override public int lastIndexOf(Object o) { throw new UnsupportedOperationException(); }
    @Override public ListIterator<U> listIterator() { throw new UnsupportedOperationException(); }
    @Override public ListIterator<U> listIterator(int i) { throw new UnsupportedOperationException(); }
    @Override public List<U> subList(int i, int i1) { throw new UnsupportedOperationException(); }
}

...
Set<String> set = getSet(...);
ListViewOfSet<String> listOfNames = new ListViewOfSet<>(set);
...

এটি আসলে একমাত্র উত্তর যা আসলে প্রশ্নের মধ্যে বর্ণিত সমস্যা সমাধান করে!
লি

আপনি অ্যাবস্ট্রাকলিস্ট প্রসারিত করে খুব সহজেই এটি বাস্তবায়ন করতে পারেন
লিই

1

আমি সেট থেকে একটি তালিকা তৈরি করতে এই কাজটি সূক্ষ্ম এবং দরকারী বলে মনে করি।

ArrayList < String > L1 = new ArrayList < String > ();
L1.addAll(ActualMap.keySet());
for (String x: L1) {
    System.out.println(x.toString());
}

-15
Map<String, List> mainMap = new HashMap<String, List>();

for(int i=0; i<something.size(); i++){
  Set set = getSet(...); //return different result each time
  mainMap.put(differentKeyName, new ArrayList(set));
}

11
আপনি তালিকা তৈরি করা এড়ানো হয়নি। এই কোডটি আপনার প্রশ্নের নমুনার মতো তুচ্ছ similar
টেলর

2
তবে এটি আপনার কুইজনের উত্তর দেয় না, উত্তর নেই বলে।
লার্নের মারকুইস
আমাদের সাইট ব্যবহার করে, আপনি স্বীকার করেছেন যে আপনি আমাদের কুকি নীতি এবং গোপনীয়তা নীতিটি পড়েছেন এবং বুঝতে পেরেছেন ।
Licensed under cc by-sa 3.0 with attribution required.