Ищем способ создания случайных чисел параллельно с семенами. Нужны результаты, чтобы быть последовательными по всем пробегам и уникальными.
В приведенном ниже коде доступ к Random из нескольких потоков приводит к сбою обоих утверждений. Random не является потокобезопасным, так что этого следовало ожидать. Используя SplittableRandom , я ожидал получить уникальные и согласованные результаты (оба утверждения), не работает. Использование ThreadLocalRandom не имеет начального числа и, следовательно, не может обеспечить согласованные результаты.
public static void main(String[] args){
List<List<Double>> randomLists = IntStream.range(0,100)
.mapToObject(j->getNextList(new Random(42)).collect(toList());
validateListsHoldUniqueNumbers(list);
validateListsAreIdentical(list);
}
// original random
public static List<Double> getNextList(Random random){
return IntStream.range(0,100).parallel.mapToDouble(i->random.nextLong()).sorted().boxed().collect(toList));
}
public static void validateListsHoldUniqueNumbers(List<List<Double>> randomLists){
randomLists.forEach(randomList -> assert(new HashSet<>(randomList).size() == randomList.size());
}
public static void validateListsAreIdentical(List<List<Double>> randomLists){
assert(new HashSet<>(randomLists).size() == 1)
}
Это код SplittableRandom, ожидалось, что он является поточно-безопасным - не работал:
public static void main(String[] args){
List<List<Double>> randomLists = IntStream.range(0,100)
.mapToObject(j->getNextListSplittable(new SplittableRandom(42)).collect(toList());
validateListsHoldUniqueNumbers(list);
validateListsAreIdentical(list);
}
public static List<Double> getNextListSplittable(SplittableRandom random){
return IntStream.range(0,100).parallel.mapToDouble(i->random.split().nextLong()).sorted().boxed().collect(toList));
}
Правильно ли используется splittable? Это действительно потокобезопасный?