【MPI】并行奇偶交换排序
typedef long long __int64;
#include "mpi.h"
#include <cstdio>
#include <algorithm>
#include <cmath>
using namespace std;
int Compute_partner(int phase,int my_rank,int comm_sz){//根据趟数的奇偶性以及当前编号的编号得到partner进程的编号
int partner;
if(!(phase&1)){
if(my_rank&1){
partner=my_rank-1;
}
else{
partner=my_rank+1;
}
}
else{
if(my_rank&1){
partner=my_rank+1;
}
else{
partner=my_rank-1;
}
}
if(partner==-1 || partner==comm_sz){
partner=MPI_PROC_NULL;
}
return partner;
}
int main(int argc, char* argv[]){
int my_rank=0, comm_sz=0;
MPI_Init(&argc, &argv);
MPI_Comm_rank(MPI_COMM_WORLD, &my_rank);
MPI_Comm_size(MPI_COMM_WORLD, &comm_sz);
int np,n,local_n;//分别为进行奇偶交换排序的趟数和读入的数据总量以及分成的每段的长度
FILE* fp;
if(my_rank==0){
fp=fopen("Sort.txt","r");
fscanf(fp,"%d%d",&np,&n);
local_n=n/comm_sz;
}
MPI_Bcast(&np,1,MPI_INT,0,MPI_COMM_WORLD);
MPI_Bcast(&local_n,1,MPI_INT,0,MPI_COMM_WORLD);
int* keys;
int* my_keys=new int[local_n];
if(my_rank==0){
keys=new int[n];
for(int i=0;i<n;++i){
fscanf(fp,"%d",&keys[i]);
}
fclose(fp);
}
double beginTime = MPI_Wtime();
MPI_Scatter(keys,local_n,MPI_INT,my_keys,local_n,MPI_INT,0,MPI_COMM_WORLD); //sort(my_keys,my_keys+local_n);//串行快速排序 for(int i=0;i<local_n;++i){//串行奇偶交换排序
if(!(i&1)){
for(int j=0;j+1<local_n;j+=2){
if(my_keys[j]>my_keys[j+1]){
swap(my_keys[j],my_keys[j+1]);
}
}
}
else{
for(int j=1;j+1<local_n;j+=2){
if(my_keys[j]>my_keys[j+1]){
swap(my_keys[j],my_keys[j+1]);
}
}
}
} int* recv_keys=new int[local_n];
int* temp_keys=new int[local_n];
for(int i=0;i<np;++i){
int partner=Compute_partner(i, my_rank, comm_sz);
if (partner != MPI_PROC_NULL){
MPI_Sendrecv(my_keys, local_n, MPI_INT, partner, 0, recv_keys, local_n, MPI_INT, partner, 0, MPI_COMM_WORLD, MPI_STATUS_IGNORE);
if(my_rank<partner){//编号小的进程留下归并时较小的一半
int e=0,e1=0,e2=0;
int* temp_keys=new int[local_n];
while(e<local_n){
if(my_keys[e1]<=recv_keys[e2]){
temp_keys[e]=my_keys[e1];
++e;
++e1;
}
else{
temp_keys[e]=recv_keys[e2];
++e;
++e2;
}
}
for(int j=0;j<local_n;++j){
my_keys[j]=temp_keys[j];
}
}
else{//编号大的进程留下归并时较大的一半
int e=local_n-1,e1=local_n-1,e2=local_n-1;
while(e>=0){
if(my_keys[e1]>=recv_keys[e2]){
temp_keys[e]=my_keys[e1];
--e;
--e1;
}
else{
temp_keys[e]=recv_keys[e2];
--e;
--e2;
}
}
for(int j=0;j<local_n;++j){
my_keys[j]=temp_keys[j];
}
}
}
}
MPI_Gather(my_keys, local_n, MPI_INT, keys, local_n, MPI_INT, 0, MPI_COMM_WORLD);
double endTime = MPI_Wtime();
if (my_rank == 0){
for(int i=0;i<n;++i){
printf("%d ",keys[i]);
}
puts("");
printf("spent time = %lf second\n", endTime - beginTime);
}
delete[] keys;
delete[] my_keys;
delete[] recv_keys;
delete[] temp_keys;
MPI_Finalize();
return 0;
}
【MPI】并行奇偶交换排序的更多相关文章
- MPI 并行奇偶交换排序 + 集合通信函数 Sendrecv() Sendvecv_replace()
▶ <并行程序设计导论>第三章的例子程序 ● 代码 #include <stdio.h> #include <mpi.h> #include <stdlib. ...
- MPI实现并行奇偶排序
奇偶排序 odd-even-sort, using MPI 代码在 https://github.com/thkkk/odd-even-sort 使用 MPI 实现奇偶排序算法, 并且 MPI 进程 ...
- 【MPI学习6】MPI并行程序设计模式:具有不连续数据发送的MPI程序设计
基于都志辉老师<MPI并行程序设计模式>第14章内容. 前面接触到的MPI发送的数据类型都是连续型的数据.非连续类型的数据,MPI也可以发送,但是需要预先处理,大概有两类方法: (1)用户 ...
- 【MPI学习2】MPI并行程序设计模式:对等模式 & 主从模式
这里的内容主要是都志辉老师<高性能计算之并行编程技术——MPI并行程序设计> 书上有一些代码是FORTAN的,我在学习的过程中,将其都转换成C的代码,便于统一记录. 这章内容分为两个部分: ...
- C++程序中调用MPI并行的批处理命令
问题来源:在使用MPI时,将程序并行实现了,运行时需要在dos窗口下输入批处理命令,以完成程序的执行. 如:mpiexec -localroot -n 6 d:/mpi/pro.exe 但每次这样挺麻 ...
- 【MPI学习7】MPI并行程序设计模式:MPI的进程组和通信域
基于都志辉老师MPI编程书中的第15章内容. 通信域是MPI的重要概念:MPI的通信在通信域的控制和维护下进行 → 所有MPI通信任务都直接或间接用到通信域这一参数 → 对通信域的重组和划分可以方便实 ...
- 【MPI学习4】MPI并行程序设计模式:非阻塞通信MPI程序设计
这一章讲了MPI非阻塞通信的原理和一些函数接口,最后再用非阻塞通信方式实现Jacobi迭代,记录学习中的一些知识. (1)阻塞通信与非阻塞通信 阻塞通信调用时,整个程序只能执行通信相关的内容,而无法执 ...
- 学习MPI并行编程记录
简单的MPI程序示例 首先,我们来看一个简单的MPI程序实例.如同我们学习各种语言的第一个程序一样,对于MPI的第一个程序同样是"Hello Word". /* Case 1 he ...
- 【MPI学习5】MPI并行程序设计模式:组通信MPI程序设计
相关章节:第13章组通信MPI程序设计. MPI组通信与点到点通信的一个重要区别就是:组通信需要特定组内所有成员参与,而点对点通信只涉及到发送方和接收方. 由于需要组内所有成员参与,因此也是一种比较复 ...
随机推荐
- 【洛谷】【洛谷月赛】4月月赛Round 1/2
洛谷月赛“月”来“月”丧了,一月更比一月丧,做得我十分不“月”…… 4月的两轮月赛,都只会T1,就写一下吧,等待后续更新…… 先看看Round1的T1: [R1T1] 网址:点我 [题意简述] 给定一 ...
- python的面对对象
创建类 使用 class 语句来创建一个新类,class 之后为类的名称并以冒号结尾: class ClassName: '类的帮助信息' #类文档字符串 class_suite #类体 类的帮助信息 ...
- 服务发现 consul cluster 的搭建
consul cluster setup 介绍和指南: consul用于服务发现.当底层服务发生变化时,能及时更新正确的mysql服务IP. 并提供给业务查询.但需要自行编写脚本,监测数据库状态和切断 ...
- Webmin试玩
安装: # cd /opt # wget http://www.webmin.com/jcameron-key.asc # wget http://www.webmin.com/download/rp ...
- MySQL基础 - 权限配置
为数据库创建特定的用户和密码 mysql>grant all privileges on <database>.* to '<username>'@'localhost' ...
- Java 容器的打印
Java容器类库中的两种主要类型,它们的区别在于容器中每个"槽"保存的元素个数 Clollection容器只能在保存一个元素,此类容器包括: List,它以特定顺序保存一组元素 S ...
- LeetCode403. Frog Jump
A frog is crossing a river. The river is divided into x units and at each unit there may or may not ...
- HBase 入门笔记-数据落地篇
一.前言 关于数据落地方面,HBase官网也有相关介绍.本文主要介绍一下实际工作中涉及的数据存储方面的一些经验和技巧,主要涉及表rowkey设计.数据落地方案 二.表设计 相对于MySQL等关系型数据 ...
- 微信小程序蓝牙模块
蓝牙部分知识 关于Service: 每个设备包含有多个Service,每个Service对应一个uuid 关于Characteristic 每个Service包含多个Characteristic,每个 ...
- shell常用
-e filename 如果 filename存在,则为真-d filename 如果 filename为目录,则为真 -f filename 如果 filename为常规文件,则为真-L filen ...