হ্যাশম্যাপের মানগুলি পুনরাবৃত্তি এবং অনুলিপি করার কার্যকর উপায়


9

আমি রূপান্তর করতে চাই:

Map<String, Map<String, List<Map<String, String>>>> inputMap 

প্রতি:

Map<String, Map<String, CustomObject>> customMap

inputMapকনফিগারেশনে সরবরাহ করা হয় এবং প্রস্তুত তবে আমার customMapফর্ম্যাট করা দরকার । কোনও List<Map<String, String>>ফাংশনে কোডের কয়েকটি লাইন ব্যবহার করে কাস্টমবজেক্টটি উত্পন্ন করা হবে ।

আমি ইনপুট মানচিত্রের পুনরাবৃত্তি এবং কাস্টম্যাপে কী মানগুলি অনুলিপি করার একটি সাধারণ উপায় চেষ্টা করেছি। জাভা 8 বা অন্য কোনও শর্টকাট ব্যবহার করে এমন করার কোনও কার্যকর উপায় আছে কি?

Map<String, Map<String, List<Map<String, String>>>> configuredMap = new HashMap<>();
Map<String, Map<String, CustomObj>> finalMap = new HashMap<>();


for (Map.Entry<String, Map<String, List<Map<String, String>>>> attributeEntry : configuredMap.entrySet()) {
    Map<String, CustomObj> innerMap = new HashMap<>();
    for (Map.Entry<String, List<Map<String, String>>> valueEntry : attributeEntry.getValue().entrySet()) {
        innerMap.put(valueEntry.getKey(), getCustomeObj(valueEntry.getValue()));
    }
    finalMap.put(attributeEntry.getKey(), innerMap);
}

private CustomObj getCustomeObj(List<Map<String, String>> list) {
    return new CustomObj();
}

কোডটি সঠিকভাবে ফর্ম্যাট করুন।
আকুজমিনিখ

1
আপনি অনুলিপি না করে একটি মুখোমুখি তৈরি সম্পর্কে চিন্তাভাবনা করেছেন?
কন্ট্রোলআল্টেল

এর চেয়ে কার্যকর কোনও উপায় আর হতে পারে না। এই সমস্ত অপারেশন করতে হবে। কিন্তু এই কোডটি আসলে কাজ করে না। আপনি কাস্টম অবজেক্টে তালিকাটি রাখছেন না।
ব্যবহারকারী 207421

উত্তর:


2

ওয়ান সমাধান স্ট্রিম হয় entrySetএর inputMap, এবং তারপর ব্যবহার Collectors#toMapদুইবার (বাইরের জন্য একবার Mapএবং ভিতরের জন্য একবার Map):

Map<String, Map<String, CustomObj>> customMap = inputMap.entrySet()
        .stream()
        .collect(Collectors.toMap(Function.identity(), entry -> {
            return entry.getValue()
                        .entrySet()
                        .stream()
                        .collect(Collectors.toMap(Function.identity(), 
                            entry -> getCustomeObj(entry.getValue())));
        }));

{}ল্যাম্বডায় আপনি এবং রিটার্নের বিবৃতিটি বাদ দিতে পারেন, এরকম কিছু:.collect(Collectors.toMap(Function.identity(), entry -> entry.getValue() .entrySet() .stream() .collect(Collectors.toMap(Function.identity(), entry -> getCustomeObj(entry.getValue()))); ));
শোকো

3
@ শুকো সত্য, তবে আমি মনে করি এটি ব্লক ছাড়া কম পঠনযোগ্য বলে মনে হবে।
জ্যাকব জি।

1

আপনি স্ট্রিম করতে পারেন, তবে তা পঠনযোগ্য দেখতে পাবে না; কমপক্ষে আমার কাছে সুতরাং আপনার যদি কোনও পদ্ধতি থাকে:

static CustomObject fun(List<Map<String, String>> in) {
    return .... // whatever processing you have here
}

আপনি এখনও java-8বাক্য গঠন ব্যবহার করতে পারেন , তবে অন্যরকম:

    Map<String, Map<String, CustomObject>> customMap = new HashMap<>();

    inputMap.forEach((key, value) -> {

        value.forEach((innerKey, listOfMaps) -> {

            Map<String, CustomObject> innerMap = new HashMap<>();
            innerMap.put(innerKey, fun(listOfMaps));
            customMap.put(key, innerMap);

        });
    });

আপনি যদি অভ্যন্তরীণ মানচিত্রটি তৈরি করতে পারেন তবে আপনি immutableএটি আরও ছোট করে তুলতে পারেন:

inputMap.forEach((key, value) -> {
      value.forEach((innerKey, listOfMaps) -> {
          customMap.put(key, Collections.singletonMap(innerKey, fun(listOfMaps)));
      });
});

1

আইএমএইচও স্ট্রিমিং এত খারাপ ধারণা নয়। কোনও খারাপ সরঞ্জাম নেই। এটি কীভাবে আপনি তাদের ব্যবহার করছেন তার উপর নির্ভর করে।


এই বিশেষ ক্ষেত্রে আমি পুনরাবৃত্তি প্যাটার্নটি একটি ইউটিলিটি পদ্ধতিতে উত্তোলন করব:

public static <K, V1, V2> Map<K, V2> transformValues(Map<K, V1> map, Function<V1, V2> transformer) {
    return map.entrySet()
              .stream()
              .collect(toMap(Entry::getKey, e -> transformer.apply(e.getValue())));
}

উপরের পদ্ধতিটি যে কোনও পদ্ধতির ব্যবহার করে প্রয়োগ করা যেতে পারে, যদিও আমি মনে করি যে Stream APIএখানে বেশ ভাল ফিট করে।


একবার আপনি ইউটিলিটি পদ্ধতিটি সংজ্ঞায়িত করলে, এটি নীচের মত সহজ হিসাবে ব্যবহার করা যেতে পারে:

Map<String, Map<String, CustomObj>> customMap = 
    transformValues(inputMap, attr -> transformValues(attr, this::getCustomObj));

আসল রূপান্তর কার্যকরভাবে একটি লাইনার। যথাযথ সহJavaDoctransformValuesপদ্ধতির জন্য ফলাফল কোড বেশ পঠনযোগ্য এবং রক্ষণাবেক্ষণযোগ্য।


1

Collectors.toMapবাহ্যিক এবং অভ্যন্তরীণ স্তরে যেমন এন্ট্রিগুলি সম্পর্কে কীভাবে :

Map<String, Map<String, CustomObj>> finalMap = configuredMap.entrySet()
        .stream()
        .collect(Collectors.toMap(Map.Entry::getKey,
                attributeEntry -> attributeEntry.getValue().entrySet()
                        .stream()
                        .collect(Collectors.toMap(Map.Entry::getKey,
                                valueEntry -> getCustomeObj(valueEntry.getValue())))));
আমাদের সাইট ব্যবহার করে, আপনি স্বীকার করেছেন যে আপনি আমাদের কুকি নীতি এবং গোপনীয়তা নীতিটি পড়েছেন এবং বুঝতে পেরেছেন ।
Licensed under cc by-sa 3.0 with attribution required.