Parallel Stream
برای موازی کردن پردازش ها در زمان استفاده از کلاس استریم باید توجه به Race Condition ها در ناحیه اشتراکی داشته باشید در مثال زیر سعی شده این مطلب به سادگی نمایش داده بشه!
کلاسی ایجاد شده است که به جای یک Consumer اینترفیس که در تکرار گر Foreach استریم استفاده شده که کار جمع کردن مقادیر را به عهده داره همونطور که مشاهده میکنید در مثال اول بدون هیچگونه همگام سازی با استفاده از parallel موازی سازی انجام شده که مطمئنا Race Condition رخ میده برای رفع این مشکل از ناحیه اشتراکی همگام سازی شده Synchronization جاوا استفاده نشده به علت مسائلی که داره Thread Yield با کاهش وحشتناک سرعت روبه رو خواهیم شد. به همین علت در مثال دوم از کتابخانه Atomic جاوا و کلاس LongAddr استفاده میکنیم تا این مشکل تداخل در دستیابی به داده اشتراکی را رفع کنیم.

private static class person {

String name;
int salary ;

person(String name, int salary) {
this.name = name;
this.salary = salary;
}

String getName() {
return this.name;
}
int getSalary(){
return this.salary;
}
}

static class SalarySum {
static int total ;

static void accept(person p) {
total += p.getSalary(); //race condition unpredictable wrong results!!
}

int getTotal() {
return total;
}
}

public static void main(String[] args) {

List<person> personList = new ArrayList<>();
personList.add(new person("a",1000));
personList.add(new person("b",2000));
personList.add(new person("c",3000));
SalarySum salarySum = new SalarySum();
personList.stream()
.parallel()
.forEach(SalarySum::accept);
int totalSalary = salarySum.getTotal();

}


اصلاح مشکل ...

private static class person {

String name;
int salary ;

person(String name, int salary) {
this.name = name;
this.salary = salary;
}

String getName() {
return this.name;
}
int getSalary(){
return this.salary;
}
}

static class SalarySum {
static LongAdder totalSync = new LongAdder();

static void acceptSync(person p) {
totalSync.add(p.getSalary());
}
long getTotalSync() {
return totalSync.longValue();
}
}

public static void main(String[] args) {

List<person> personList = new ArrayList<>();
personList.add(new person("a",1000));
personList.add(new person("b",2000));
personList.add(new person("c",3000));
SalarySum salarySum = new SalarySum();

personList.stream()
.parallel()
.forEach(SalarySum::acceptSync);
long totalSalary2 = salarySum.getTotalSync();
}