Этот пример показывает, как улучшить скорость выполнения систем связи с использованием симуляций BER. Чтобы улучшить эффективность этих систем, одним из доступных опций является параллелизация симуляций. Этот пример представляет использование Parallel Computing Toolbox™ (PCT) в симуляциях BER. Он представляет два возможных способа параллелизации симуляций BER и рекомендует лучший метод.
В этом разделе проверяется доступность PCT. При наличии он открывает параллельный пул работников и присваивает переменной numWorkers максимальное количество доступных работников в пуле. Если он недоступен, он присваивает numWorkers = 1, в этом случае пример выполняется на одном ядре.
[licensePCT,~] = license( 'checkout','Distrib_Computing_Toolbox'); if ( licensePCT && ~isempty(ver('parallel'))) if isempty(gcp('nocreate')) parpool; end pool = gcp; numWorkers = pool.NumWorkers; else numWorkers = 1; end
Starting parallel pool (parpool) using the 'local' profile ... Connected to the parallel pool (number of workers: 12).
Этот пример параллелизирует пример Пространственного Мультиплексирования, чтобы продемонстрировать использование РСТ. Ниже приведены параметры, необходимые для моделирования этого примера.
EbNo = 1:2:11; % Eb/No in dB N = 2; % Number of transmit antennas M = 2; % Number of receive antennas modOrd = 2; % constellation size = 2^modOrd numBits = 1e6; % Number of bits numErrs = 100; % Number of errors lenEbNo = length(EbNo); % Create a local random stream to be used for data generation for % repeatability. Use the combined multiple recursive generator since it % supports substreams. hStr = RandStream('mrg32k3a'); % Setting the random stream [berZF,berMMSE] = deal(zeros(lenEbNo,3)); [nerrsZF,nbitsZF,nerrsMMSE,nbitsMMSE] = deal(zeros(numWorkers,lenEbNo));
Первый метод параллелизируется между областью значений Eb/No, где один рабочий обрабатывает одно значение Eb/No. Здесь эффективность ограничена временем, необходимым для обработки максимального значения Eb/No.
simIndex = 1; str = 'Across the Eb/No range'; disp('Performing BER simulations with one worker processing one Eb/No value ...');
Performing BER simulations with one worker processing one Eb/No value ...
tic parfor idx = 1:lenEbNo [BER_ZF,BER_MMSE] = simBERwithPCT(N,M,EbNo,modOrd, ... idx,hStr,numBits,numErrs); berZF(idx,:) = BER_ZF(idx,:); berMMSE(idx,:) = BER_MMSE(idx,:); end timeRange = toc; clockBERwithPCT(simIndex,timeRange,timeRange,str);
Второй метод параллелизируется по количеству доступных работников, где каждый рабочий процесс обрабатывает полную область значений Eb/No. Однако каждый рабочий процесс подсчитывает (всего ошибок/numWorkers) ошибки перед переходом к следующему значению Eb/No. Этот метод одинаково эффективно использует все доступные ядра.
simIndex = simIndex + 1; str = 'Across the number of available workers'; seed = 0:numWorkers-1; disp('Performing BER simulations with each worker processing the entire range ...');
Performing BER simulations with each worker processing the entire range ...
tic parfor n = 1:numWorkers hStr = RandStream('mrg32k3a','Seed',seed(n)); for idx = 1:lenEbNo [BER_ZF,BER_MMSE] = simBERwithPCT(N,M,EbNo,modOrd, ... idx,hStr,numBits/numWorkers,numErrs/numWorkers); nerrsZF(n,idx) = BER_ZF( idx,2); nbitsZF(n,idx) = BER_ZF( idx,3); nerrsMMSE(n,idx) = BER_MMSE(idx,2); nbitsMMSE(n,idx) = BER_MMSE(idx,3); end end bZF = sum(nerrsZF,1)./sum(nbitsZF,1); bMMSE = sum(nerrsMMSE,1)./sum(nbitsMMSE,1); timeWorker = toc;
Ниже приведены результаты, полученные на компьютере с ОС Windows ® 10, 64-разрядной, Intel ® Xeon ® CPU W-2133, 3.6GHz 64GB оперативной памятью с использованием шести ядер. Таблица показывает сравнение эффективности вышеуказанных методов. Мы видим, что второй метод работает лучше, чем первый. Это результаты, полученные за один запуск, которые могут варьироваться от прогона до прогона.
-------------------------------------------------------------------------------------------- Type of Parallelization | Elapsed Time (sec)| Speedup Ratio 1. Across the Eb/No range | 1.9986 | 1.0000 2. Across the number of available workers | 0.8362 | 2.3902 --------------------------------------------------------------------------------------------
График ниже показывает кривые BER, полученные для нулей принуждением (ZF) и минимальной средней квадратичной невязкой (MMSE) с использованием различных методов параллелизации.
plotBERwithPCT(EbNo,berZF(:,1),berMMSE(:,1),bZF,bMMSE);
Чтобы сгенерировать таблицу сравнения эффективности для вашей машины, раскомментируйте следующую строку кода и запустите весь этот скрипт.
% clockBERwithPCT(simIndex,timeRange,timeWorker,str);
В этом примере используются следующие функции: