Управление параллелизмом и вложенными параллельными коллекциями scala

Мне очень трудно понять это поведение параллельных коллекций в Scala.

import java.util.concurrent.TimeUnit
import scala.collection.parallel.ForkJoinTaskSupport

object test extends App {

  val CHANGE_ME = false

  val externalParallelism = if (CHANGE_ME) 10 else 2

  val l = (1 until 100).par
  val l2 = List(1).par // par but with only one element

  l2.tasksupport = new ForkJoinTaskSupport(
    new scala.concurrent.forkjoin.ForkJoinPool(externalParallelism))
  l.tasksupport = new ForkJoinTaskSupport(new scala.concurrent.forkjoin.ForkJoinPool(2))

  l2.map { j =>
    l.map { i =>
      println(s"STARTED $i")
      TimeUnit.SECONDS.sleep(10) // blocking
      println(s"DONE $i")
    }
  }
}

Если приведенный выше код запускается с CHANGE_ME = false, вы увидите

STARTED 1
STARTED 50

показывая, что текущий параллелизм равен 2, и это правильно, поскольку внутренняя параллельная коллекция l связана с поддержкой задач с помощью пула потоков fork-join с параллелизмом 2. Если сейчас вы установите CHANGE_ME = true, вы будете удивительно наблюдать

STARTED 87
STARTED 93
STARTED 13
STARTED 25
STARTED 75
STARTED 56
STARTED 62
STARTED 50
STARTED 1

свидетельство того, что внутренняя параллельная коллекция использует потоки, которые должны быть связаны с внешней параллельной коллекцией. Это ожидаемое поведение? Как тогда может быть связан параллелизм l?

0 ответов

Другие вопросы по тегам