Управляйте потоками случайных чисел на рабочих

Функции генерации случайных чисел rand, randi, и randn ведите себя по-другому для параллельных вычислений по сравнению с вашим MATLAB® клиент. Можно изменить поведение генераторов случайных чисел на параллельных рабочих или на клиенте, чтобы сгенерировать восстанавливаемые потоки случайных чисел.

По умолчанию клиент MATLAB и работники MATLAB используют различные генераторы случайных чисел, даже если рабочие являются частью локального кластера на той же машине как клиент. Приведенная ниже таблица обобщает настройки по умолчанию для клиента и рабочих:

 ГенераторSeedНормальное преобразование
Клиент'Twister' или 'mt19937ar'0'Ziggurat'
Рабочий (локальный или удаленный)'Threefry' или 'Threefry4x64_20'0'Inversion'

Для получения дополнительной информации о доступных генераторах и нормальных преобразованиях, смотрите Выбор Random Number Generator. Каждый рабочий в кластере чертит случайные числа от независимого потока со свойствами в таблице. По умолчанию случайные числа сгенерированы на каждом рабочем в a parfor цикл отличается друг от друга и от случайных чисел, сгенерированных на клиенте.

Примечание

Если у вас есть графический процессор на вашем рабочем, различные настройки применяются к потокам случайных чисел на графическом процессоре. Для получения дополнительной информации смотрите Потоки Случайных чисел на графическом процессоре.

Клиент и рабочие

Если необходимо сгенерировать тот же поток чисел в клиенте и рабочих, можно установить совпадать с другим. Можно установить алгоритм генератора и использование seed rng.

Например, вы можете запустить скрипт как пакетное задание на рабочем, и нуждаться в том же генераторе или последовательности как клиент. Предположим, что вы начинаете с файла с именем скрипта randScript1.m это содержит линию:

R = rand(1,4);

Можно запустить этот скрипт в клиенте, и затем как пакетное задание на рабочем. Заметьте, что сгенерированные последовательности значения по умолчанию случайных чисел в результатах отличаются.

randScript1; % In client
R
R =
    0.8147    0.9058    0.1270    0.9134
parallel.defaultClusterProfile('local')
c = parcluster();
j = batch(c,'randScript1'); % On worker
wait(j);load(j);
R
R =
    0.1349    0.6744    0.9301    0.5332

Для идентичных результатов можно установить клиент и рабочего использовать тот же генератор и seed. Здесь, файл randScript2.m содержит следующий код:

rng(1,'Threefry');
R = rand(1,4);

Теперь запустите новый скрипт в клиенте и на рабочем:

randScript2; % In client
R
R =
    0.1404    0.8197    0.1073    0.4131
j = batch(c,'randScript2'); % On worker
wait(j); load(j);
R
R =
    0.1404    0.8197    0.1073    0.4131

Различные рабочие

По умолчанию у каждого рабочего в кластере, работающем над тем же заданием, есть независимый поток случайных чисел. Если rand, randi, или randn называются параллельно, каждый рабочий производит уникальную последовательность случайных чисел.

Примечание

Поскольку rng('shuffle') отбирает генератор случайных чисел на основе текущего времени, не используйте эту команду, чтобы установить поток случайных чисел на различных рабочих, если вы хотите гарантировать независимые потоки. Это особенно верно, когда команда отправляется нескольким рабочим одновременно, такой как в parforSPMD, или связывающееся задание. Для независимых потоков на рабочих используйте поведение по умолчанию; или если это не достаточно для ваших потребностей, рассмотрите использование уникального подпотока на каждом рабочем, использующем RandStream.

Этот пример использует двух рабочих в параллельном пуле, чтобы показать, что они генерируют уникальные последовательности случайных чисел.

p = parpool(2);
spmd
    R = rand(1,4); % Different on each worker
end
R{1},R{2}
ans = 
    0.1349    0.6744    0.9301    0.5332
ans =
    0.6383    0.5195    0.1398    0.6509
delete(p)

Если вам нужны все рабочие, чтобы сгенерировать ту же последовательность чисел, можно установить каждого рабочего использовать те же настройки генератора:

p = parpool(2);
spmd
    rng(0,'Philox'); % Default seed 0.
    R = rand(1,4); % Same on all workers
end
R{1},R{2}
ans =
    0.3655    0.6975    0.1789    0.4549
ans =
    0.3655    0.6975    0.1789    0.4549
delete(p)

Если необходимо управлять случайными числами в каждой итерации parfor- цикл, смотрите Повторные Случайные числа в циклах parfor.

Нормально распределенные случайные числа

Если вы работаете с нормально распределенными случайными числами с помощью randn функция, можно использовать те же методы как выше использования RandStream установить тип генератора, seed и нормальный алгоритм преобразования на каждом рабочем и клиенте.

Например, предположите файл randScript3.m содержит код:

stream = RandStream('Threefry','Seed',0,'NormalTransform','Inversion');
RandStream.setGlobalStream(stream);
R = randn(1,7)
Можно запустить этот код по клиенту и по рабочему в параллельном задании (использование batch или spmd) произвести ту же последовательность случайных чисел:
R =
    -0.3479    0.1057    0.3969    0.6544   -1.8228    0.9587    0.5360

Смотрите также

|

Похожие темы