প্রতিটি অনুরোধ আইটেমের জন্য একাধিক থ্রেড কীভাবে তৈরি করবেন


9

আমি অর্ডার স্তরে মাল্টিথ্রেডিং ব্যবহার করে নীচের কোডটি প্রক্রিয়া করার চেষ্টা করছি।

List<String> orders = Arrays.asList("order1", "order2", 
                   "order3", "order4", "order1");

বর্তমান ক্রমিক ক্রিয়াকলাপ:

orders.stream().forEach(order -> {
    rules.forEach(rule -> {
        finalList.add(beanMapper.getBean(rule)
                .applyRule(createTemplate.apply(getMetaData.apply(rule), command),
                           order));
    });
});

আমি ব্যবহার করে চেষ্টা করেছি:

orders.parallelStream().forEach(order -> {}} // code snippet.

তবে এটি নিয়মগুলি পরিবর্তন করছে for প্রতিটি (বিধি -> {}} অর্ডার)।

উদাহরণস্বরূপ:
ইনপুট:

 List<String> orders = Arrays.asList("order1", "order2", 
                         "order3", "order4", "order1");
 List<String> rules = Arrays.asList("rule1", "rule2", "rule3");

প্রত্যাশিত আউটপুট:

order1 with rule1, rule2, rule3
order2 with rule1, rule2, rule3

এর সাথে আসল আউটপুট parallelStream():

order1 with rule3, rule1, rule2
order1 with rule2, rule1, rule3

আমি আদেশ সম্পর্কে বিরক্ত নই আদেশ , কিন্তু আমি অঁ্যা সম্পর্কে ক্রম বিরক্ত করছি নিয়ম । আদেশগুলি যে কোনও ক্রমে প্রক্রিয়া করতে পারে, তবে প্রতিটি আদেশের জন্য নিয়মগুলি একই ক্রমে কার্যকর করা উচিত।

সাহায্য করুন.

উত্তর:


4

তুমি ব্যবহার করতে পার :

orders.stream().parallel().forEachOrdered(// Your rules logic goes here. )

স্ট্রিমের অর্ডার বজায় রাখার জন্য ফরইচঅর্ডারড গ্যারান্টি দেয়।

সুতরাং আপনার রেফারেন্সের জন্য:

orders.stream().parallel().forEachOrdered( order -> {

            rules.stream().parallel().forEachOrdered ( rule -> {

                 System.out.println( " Order : " + order + " rule :" + rule);
            });

        });

দ্রষ্টব্য: আমরা এটি করতে পারার সময়, পারফরম্যান্সটি ঘনিষ্ঠভাবে পর্যবেক্ষণ করা উচিত কারণ প্যারেলিলেিজম এবং শৃঙ্খলা একে অপরের সাথে খুব ভাল বিয়ে করে না!

আউটপুট

 Order : order1 rule :rule1
 Order : order1 rule :rule2
 Order : order1 rule :rule3
 Order : order2 rule :rule1
 Order : order2 rule :rule2
 Order : order2 rule :rule3
 Order : order3 rule :rule1
 Order : order3 rule :rule2
 Order : order3 rule :rule3
 Order : order4 rule :rule1
 Order : order4 rule :rule2
 Order : order4 rule :rule3
 Order : order1 rule :rule1
 Order : order1 rule :rule2
 Order : order1 rule :rule3

উত্তরের জন্য ধন্যবাদ. forEachOrused স্ট্রিমের ক্রমর গ্যারান্টি দেয় তবে তারপরে এটি কার্য সম্পাদনকে ধীর করে দেয়। আমি এটি চেষ্টা করেছি এবং অ্যাপ্লিকেশনটি অনুক্রমিক প্রক্রিয়াজাতকরণের অনুরূপ সময় নিচ্ছে। স্ট্রিম ()। সমান্তরাল এবং forOachOrused একে অপরের প্রশংসা করে না।
মায়াঙ্ক বিশ্ট

হ্যাঁ আমি সম্মত হলাম এটি করার আগে আমাদের সম্পূর্ণ বিলম্বিত বিশ্লেষণ করা দরকার need
প্রমোদ এস নিকম

হ্যাঁ, আমি এটি ব্যবহার করে একই পারফরম্যান্স পাচ্ছি, কোনও উন্নতি হচ্ছে না।
মায়াঙ্ক বিশট

1
এটি করার আরও ভাল সমাধান পেতে নিবিড়ভাবে এই থ্রেডটি অনুসরণ করুন।
প্রমোদ এস নিকম

আমি কি এক্সিকিউটর সার্ভিস ব্যবহার করে সমান্তরাল প্রক্রিয়াকরণ অর্জন করতে পারি?
মায়াঙ্ক বিশট

1

আপনি finalListএকই সাথে বিভিন্ন থ্রেড থেকে উপাদানগুলিতে যুক্ত করেন। এটি বিভিন্ন আদেশে বিধি প্রয়োগের মিশ্রিত ফলাফলের কারণ হয়ে উঠছে (নিয়মগুলি তাদের আদেশ অনুসারে গোষ্ঠীকরণ করা হচ্ছে না)।

আপনি এটির জন্য orderপ্রতিটিের জন্য একটি অস্থায়ী তালিকা তৈরি করে ঠিকঠাক করতে পারেন এবং তারপরে একটিতে সমস্ত অস্থায়ী তালিকাগুলি সিঙ্ক্রোনালি মেশানো finalList

এখানে আপনি স্ট্রিম-এপিআই (জাভা 9+) ব্যবহার করে কীভাবে তা করতে পারেন তা এখানে:

List<AppliedRule> finalList = orders.parallelStream().map(order ->
        rules.stream().map(rule -> applyRule(order, rule)).collect(Collectors.toList())
).collect(Collectors.flatMapping(Collection::stream, Collectors.toList()));

দ্রষ্টব্য: স্ট্রিম সংগ্রহের সময় সমকালীনভাবে ফ্ল্যাট ম্যাপিং চালানোর জন্য সরলের Collectors.flatMapping()পরিবর্তে এখানে ব্যবহৃত হয় flatMap


জাভা 8 এনালগ:

List<AppliedRule> finalList = orders.parallelStream().map(order ->
        rules.stream().map(rule -> applyRule(order, rule)).collect(Collectors.toList())
).collect(Collectors.toList())
        .stream()
        .flatMap(Collection::stream)
        .collect(Collectors.toList());

উত্তরের জন্য ধন্যবাদ. আমি আপনার পদ্ধতির চেষ্টা করেছি এবং আমি java.util.ConcurrentModificationsException পেয়েছি: নাল
mayank bisht

ফাইনাললিস্ট = অর্ডার.প্যারালাল স্ট্রিম () .ম্যাপ (অর্ডার -> নিয়ম.প্রবাহ ()। মানচিত্র (বিধি -> beanMapper.getBean (নিয়ম)। অ্যাপ্লাইরুল (createTemplate.apply (getMetaData.apply (নিয়ম), আদেশ), আদেশ))) .collect (Collectors.toList ())) সংগ্রহ (Collectors.toList ()) প্রবাহ () flatMap (সংগ্রহ :: প্রবাহ) .collect (Collectors.toList (।))।।
mayank bisht

@ মায়াঙ্কবিশত, এর অর্থ এটি beanMapper.getBean(rule) .applyRule(createTemplate.apply(getMetaData.apply(rule), command), order)খাঁটি ফাংশন নয়, সুতরাং এটি সমান্তরালে ব্যবহার করা যাবে না। এটি থেকে সমস্ত পার্শ্ব প্রতিক্রিয়া অপসারণ করার চেষ্টা করুন; ConcurrentModificationExceptionস্ট্যাক ট্রেস তাদের সনাক্ত করতে সহায়তা করতে পারে।
কলা

0

এই কাজ করবে?

final int rulesSize = rules.size();
AtomicInteger atomicInteger = new AtomicInteger(0);
orders.stream().parallel().forEach(order -> {
    IntStream.range(0, rulesSize).parallel().forEach( i -> {
        synchronized (atomicInteger) {
            System.out.println(" Order : " + order + " rule :" + rules.get(atomicInteger.getAndIncrement() % rulesSize));
        }
    });
});

আউটপুট

 Order : order1 rule :rule1
 Order : order4 rule :rule2
 Order : order1 rule :rule3
 Order : order3 rule :rule1
 Order : order3 rule :rule2
 Order : order3 rule :rule3
 Order : order2 rule :rule1
 Order : order2 rule :rule2
 Order : order2 rule :rule3
 Order : order1 rule :rule1
 Order : order1 rule :rule2
 Order : order4 rule :rule3
 Order : order1 rule :rule1
 Order : order4 rule :rule2
 Order : order1 rule :rule3

0

অর্ডার ক্রম কিছু হতে পারে, তবে নিয়মের ক্রম পরিবর্তন করা উচিত নয়। এছাড়াও একটি নির্দিষ্ট আদেশের নিয়মের জন্য একটি দলে আসা উচিত।

যদি এটি হয় তবে প্রকৃত সমান্তরালতার কোনও জায়গা নেই।

কখন

order1-rule1
order1-rule2
order2-rule1
order2-rule2

এবং

order2-rule1
order2-rule2
order1-rule1
order1-rule2

2 টি আদেশ এবং 2 বিধিগুলির জন্য একমাত্র বৈধ রান
and

order1-rule1
order2-rule1
order1-rule2
order2-rule2

অবৈধ হিসাবে বিবেচিত হয়, এটি সমান্তরালতা নয়, কেবলমাত্র র্যান্ডমাইজেশন order, সম্ভবত লাভ ছাড়া। আপনি যদি order1সর্বদা প্রথম আসার সাথে "বিরক্ত" হন তবে আপনি তালিকাটি বদল করতে পারেন, তবে এটিই হ'ল:

public static void main (String[] args) throws java.lang.Exception
{
    List<String> orders = Arrays.asList("order1", "order2", "order3", "order4");
    List<String> rules = Arrays.asList("rule1", "rule2", "rule3");
    Collections.shuffle(orders);
    orders.forEach(order->{
        rules.forEach(rule->{
            System.out.println(order+"-"+rule);
        });
    });
}

এমনকি স্ট্রিমিংও প্রয়োজনীয় নয়, কেবল দুটি নেস্ট লুপ। পরীক্ষা: https://ideone.com/qI3dqd

order2-rule1
order2-rule2
order2-rule3
order4-rule1
order4-rule2
order4-rule3
order1-rule1
order1-rule2
order1-rule3
order3-rule1
order3-rule2
order3-rule3


আসল উত্তর

তবে এটি নিয়মগুলি পরিবর্তন করছে for প্রতিটি (বিধি -> {}} অর্ডার)।

না, তা হয় না। orderগুলি ওভারল্যাপ হতে পারে, কিন্তু ক্রম ruleপ্রতিটি আদেশের জন্য গুলি রাখা হয়। কেন একটি সমান্তরাল forEachঅন্য কিছু করতে হবে?

উদাহরণ কোড:

public static void main (String[] args) throws java.lang.Exception
{
    List<String> orders = Arrays.asList("order1", "order2", "order3", "order4");
    List<String> rules = Arrays.asList("rule1", "rule2", "rule3");
    orders.stream().parallel().forEach(order->{
        rules.forEach(rule->{
            System.out.println(order+"-"+rule);
        });
    });
}

পরীক্ষা: https://ideone.com/95Cybg
উদাহরণ আউটপুট:

order2-rule1
order2-rule2
order2-rule3
order1-rule1
order1-rule2
order1-rule3
order4-rule1
order4-rule2
order4-rule3
order3-rule1
order3-rule2
order3-rule3

orderS এর ক্রম মিশ্রিত হয় তবে rules সর্বদা 1-2-2 হয়। আমি মনে করি আপনার আউটপুটটি জুটিগুলি কেবল লুকিয়ে রেখেছে (আসলে আপনি কীভাবে এটি উত্পন্ন হয়েছিল তা দেখান নি)।

অবশ্যই এটি কিছু বিলম্বের সাথে বাড়ানো যেতে পারে, সুতরাং এর প্রসেসিং orderআসলে ওভারল্যাপ হয়ে যাবে:

public static void delay(){
    try{
        Thread.sleep(ThreadLocalRandom.current().nextInt(100,300));
    }catch(Exception ex){}
}

public static void main (String[] args) throws java.lang.Exception
{
    List<String> orders = Arrays.asList("order1", "order2", "order3", "order4");
    List<String> rules = Arrays.asList("rule1", "rule2", "rule3");
    orders.stream().parallel().forEach(order->{
        rules.forEach(rule->{
            delay();
            System.out.println(order+"-"+rule);
        });
    });
}

পরীক্ষা: https://ideone.com/cSFaqS
উদাহরণ আউটপুট:

order3-rule1
order2-rule1
order2-rule2
order3-rule2
order3-rule3
order2-rule3
order1-rule1
order4-rule1
order1-rule2
order4-rule2
order4-rule3
order1-rule3

এটি এমন কিছু হতে পারে যা আপনি দেখেছেন, orderxঅংশ ছাড়াই । সঙ্গে orderদৃশ্যমান গুলি এটা ট্র্যাক করা যায় যে ruleগুলি 1-2-3 আসতে থাক, প্রতিorder । এছাড়াও, আপনার উদাহরণের তালিকায় order1দু'বার রয়েছে যা অবশ্যই ঘটছে তা দেখতে সহায়তা করে নি।


উত্তরের জন্য ধন্যবাদ. উপরের আউটপুটটি কম সংখ্যক অর্ডারের জন্য সঠিক হতে পারে। আপনি যদি অর্ডারগুলি বাড়িয়ে দেন তবে আপনি আলাদা আউটপুট পাবেন। উদাহরণস্বরূপ (অর্ডার 4-বিধি 1 অর্ডার 4-বিধি 2 অর্ডার 4-বিধি 1) (অর্ডার 1-বিধি 1 আদেশ 1-নিয়ম 2) (আদেশ3-বিধি 1 আদেশ3-বিধি 2) (আদেশ4-বিধি 1 আদেশ4-বিধি 2 আদেশ4-নিয়ম 1 আদেশ4-नियम 2)
মায়াঙ্ক বিশ্ট

অর্ডার ক্রম কিছু হতে পারে, তবে নিয়মের ক্রম পরিবর্তন করা উচিত নয়। এছাড়াও একটি নির্দিষ্ট আদেশের নিয়মের জন্য একটি দলে আসা উচিত। প্রাক্তন জন্য। (order1- নিয়ম 1 order1-rule2 order1-rule3) এবং না (order1-rule1 order2-rule1 order1-rule2 order1-rule3))।
bisht মায়াঙ্ক

@ মায়াঙ্কবিশত আমি মনে করি যে এই বিধিনিষেধগুলি কেবল সমান্তরাল প্রক্রিয়াকরণের অনুমতি দেয় না। আপডেট করা উত্তর দেখুন (আমি নতুন অংশটি শুরুতে লিখেছি)।
তেভমাদার

হ্যাঁ, আমি এটি বুঝতে পারি, এবং সে কারণেই আমি এখানে এই প্রশ্নটি পোস্ট করেছি। আমি ভেবেছিলাম সম্ভবত এটি করার অন্য কোনও উপায় থাকবে, অথবা আমরা আবার আলগো পরিবর্তন করতে পারি
mayank bisht

@ মায়াঙ্কবিশত আপনি কীভাবে orderওভারল্যাপ করতে পারবেন না তা বর্ণনা করতে পারেন ( এইগুলি কি সম্ভবত রাষ্ট্রীয় rule, এবং সীমিত সংখ্যায় রয়েছে, সম্ভবত কেবল একটিই আছে?)। তবে সাধারণত জিনিসগুলিতে সমান্তরালভাবে চলমান ছাড়া কোনও সমান্তরালতা থাকে না, এটি সর্বোপরি সমান্তরালতার পুরো বিন্দু।
তেভমাদার

0

আপনি যদি তৃতীয় পক্ষের লাইব্রেরি চেষ্টা করতে আপত্তি না করেন। এখানে আমার লাইব্রেরির সাথে নমুনা দেওয়া হয়েছে: অ্যাবাকাস-ইউজ

StreamEx.of(orders).parallelStream().forEach(order -> {}}

এবং আপনি এমনকি থ্রেড নম্বর নির্দিষ্ট করতে পারেন:

StreamEx.of(orders).parallelStream(maxThreadNum).forEach(order -> {}}

অর্ডার ruleরাখা হবে।

যাইহোক, যেহেতু এটি সমান্তরাল প্রবাহে রয়েছে তাই কোডের অংশটি ...finalList.add(...সম্ভবত কাজ করবে না। আমি মনে করি ফলাফলের তালিকাতে সংগ্রহ করা ভাল:

StreamEx.of(orders).parallelStream().map/flatMap(order -> {...}}.toList()

আপনি যদি orderপরে কোনও কারণে অর্ডার রাখতে চান তবে এটি কার্যক্ষমও হবে :

StreamEx.of(orders).indexed().parallelStream()
      .map/flatMap(order -> {...}}.sortedBy(...index).toList()
আমাদের সাইট ব্যবহার করে, আপনি স্বীকার করেছেন যে আপনি আমাদের কুকি নীতি এবং গোপনীয়তা নীতিটি পড়েছেন এবং বুঝতে পেরেছেন ।
Licensed under cc by-sa 3.0 with attribution required.