Одна из базовых операций пересылки данных, необходимая при параллельной
обработке сигналов - это транспонирование двумерной матрицы. Эта
операция мотивировала обобщение функции MPI_ALLTOALLV
. Теперь
существует новая коллективная операция - MPI_ALLTOALLW
; здесь
''W
'' указывает, что она является расширением MPI_ALLTOALLV
.
Следующий вызов - это наиболее общая форма ''многие-ко-многим
''.
Подобно вызову
[]MPI_TYPE_CREATE_STRUCT
, наиболее общему типу
конструктора, MPI_ALLTOALLW
позволяет отдельно указывать счетчик,
смещение и тип данных. Кроме того, чтобы обеспечить максимальную гибкость,
смещение блоков в пределах буферов передачи и приема указывается в байтах.
Объяснение:
Функция MPI_ALLTOALLW
обобщает несколько функций MPI, тщательно
выбирая входные аргументы. Например, делая все процессы, кроме одного,
имеющими sendcounts[i] = 0
, получаем функцию MPI_SCATTERW
.
------------------------------------------------------------------
MPI_ALLTOALLW(sendbuf, sendcounts, sdispls, sendtypes,
recvbuf, recvcounts, rdispls, recvtypes,
comm)
------------------------------------------------------------------
IN | sendbuf | Стартовый адрес буфера передачи (по выбору) | ||||
IN | sendcounts | Целочисленный массив длины, равной длине группы, указывающий количество элементов для передачи каждому процессу | ||||
IN | sdispls | Целочисленный массив (длины, равной длине группы). Элемент j указывает относительное смещение в sendbuf, с которого будут браться уходящие данные, предназначенные для процесса j | ||||
IN | sendtypes | Целочисленный массив (длины, равной длине группы). Элемент j указывает тип данных для передачи процессу j (указатель) | ||||
OUT | recvbuf | Адрес буфера приема (по выбору) | ||||
IN | recvcounts | Целочисленный массив длины, равной длине группы, содержащий количество элементов, которые могут быть приняты от каждого процесса | ||||
IN | rdispls | Целочисленный массив длины, равной длине группы. Элемент i указывает относительное смещение в recvbuf, с которого будут помещаться приходящие процессу i данные | ||||
IN | recvtypes | Массив типов данных (длины, равной длине группы). Элемент i указывает тип данных, принимаемых от процесса i (указатель) | ||||
IN | comm | Коммуникатор (указатель) |
int MPI_Alltoallw(void *sendbuf, int sendcounts[],
int sdispls[], MPI_Datatype sendtypes[],
void *recvbuf, int recvcounts[],
int rdispls[], MPI_Datatype recvtypes[],
MPI_Comm comm)
MPI_ALLTOALLW(SENDBUF, SENDCOUNTS, SDISPLS, SENDTYPES, RECVBUF,
RECVCOUNTS, RDISPLS, RECVTYPES, COMM, IERROR)
<type> SENDBUF(*), RECVBUF(*)
INTEGER SENDCOUNTS(*), SDISPLS(*), SENDTYPES(*),
RECVCOUNTS(*), RDISPLS(*), RECVTYPES(*),
COMM, IERROR
void MPI::Comm::Alltoallw(const void* sendbuf, const int sendcounts[],
const int sdispls[], const MPI::Datatype sendtypes[],
void* recvbuf, const int recvcounts[],
const int rdispls[], const MPI::Datatype recvtypes[])
const = 0
Опция in-place
- не поддерживается.
-й блок, посланный из процесса получается процессом и
помещается в -й блок recvbuf
. Все эти блоки не обязательно
должны быть одинакового размера.
Сигнатура типа, связанная с sendcounts[j]
и sendtypes[j]
в
процессе должна быть эквивалентна сигнатуре типа, связанной с
recvcounts[i]
и recvtypes[i]
в процессе . Это
подразумевает, что количество переданных данных должно совпадать с
количеством полученных, попарно для каждой пары процессов. Отличные карты
типов для отправителя и получателя еще допустимы.
В исходе получаем ситуацию, аналогичную той, при которой каждый процесс сообщение каждому другому процессу с помощью
MPI_Send(sendbuf+sdispls[i], sendcounts[i], sendtypes[i],i, Е)
и получил сообщение от каждого другого процесса вызовом
MPI_Recv(recvbuf+rdispls[i], recvcounts[i], recvtypes[i],i, Е)
Все аргументы являются значимыми для всех процессов. Аргумент comm
должен описывать один коммуникатор для всех процессов.
Если comm
- интеркоммуникатор, то результатом будет посылка каждым
процессом из группы A
сообщения каждому процессу из группы
B
, и наоборот. -й буфер передачи процесса из группы
A
должен быть совместим с -м буфером приема процесса из
группы B
, и наоборот.