正则采样 自适应方法 并行正则采样排序

前言

正则采样,就是从原数组中尽量等间隔的取出采样点。

最近在学习MPI并行编程,今天手撕并行正则采样排序时遇到一个难题——如何实现正则采样? 这部分在CSDN上没人介绍,我自己琢磨了一种自适应的方法。其效果还没有进行大量测试,下面说一下我的思路。

代码

先贴出代码,后续讨论

void regular_samp(int* raw, int count, int* samp, int k)
{
    int step = floor((count - k) / (k + 1)) + 1;
    int j = 0, left = count;
    for (int i = step - 1; i < count && j < k; i += step)
    {
        samp[j++] = raw[i];
        left -= step;
        step = round(double(left - (k - j)) / (k - j + 1)) + 1;
    }
}

最初想法

上述代码实现的是从包含count个元素的raw数组中正则采样k个元素到samp数组中。

所谓正则采样,最理想的情况就是等间隔采样。

比如从 1 2 3 4 5 6 7中取3个数——2 4 6。间隔为2(两个采样数字之间的距离)

因此我最初的想法就是计算间隔(step)等于多少,从count个数中取出k个数,然后均分成k + 1段。如果下标从0开始计算,也就是说认为还有两个隐含的采样点 -1 和 count。

提出公式: s t e p = c o u n t − k k + 1 + 1 step= \frac{count - k}{k + 1} + 1 step=k+1countk+1

但很多时候分数并不整除,这时候问题来了,对于分式的结果我们向上取整还是向下取整还是四舍五入?

按我的测试,这些方案都不合适。

比如 1 2 3 4 5取3个数,最理想的结果应该是1 3 5。如果向上取整,step = 2,干脆取不到三个数。如果向下取整,step = 1,取得的是1 2 3,很不合理。

自适应方法

基本思路还是按照step的大小决定数在哪里取得。但自适应方法,就是让算法依据子问题自动决定step的大小。每次取出一个数,直到取出所有数。

原问题是从包含count个元素的raw数组中正则采样k个元素到samp数组中。取出一个数后,问题变成从count - step个数中正则采样k - 1个数。

第一个step计算我使用了向下取整方式,因为-1那个默认的采样点是不存在的,这里的间隔可以损失一些。后面则采用四舍五入方法。

粗略验证

使用6个核对0 1 2 … 1022 1023排序(每次运行前提前打乱数组),采样结果为:
在这里插入图片描述

结语

按照我在并行正则采样排序中的实践,效果还是不错的。欢迎大家指出问题。

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值