7-29 与零交换(超详细思路解析,其实可以只用数组解)

将 { 0, 1, 2, ..., N-1 } 的任意一个排列进行排序并不困难,这里加一点难度,要求你只能通过一系列的 Swap(0, *) —— 即将一个数字与 0 交换 —— 的操作,将初始序列增序排列。例如对于初始序列 { 4, 0, 2, 1, 3 },我们可以通过下列操作完成排序:

  • Swap(0, 1) ⟹ { 4, 1, 2, 0, 3 }
  • Swap(0, 3) ⟹ { 4, 1, 2, 3, 0 }
  • Swap(0, 4) ⟹ { 0, 1, 2, 3, 4 }

本题要求你找出将前 N 个非负整数的给定排列进行增序排序所需要的最少的与 0 交换的次数。

输入格式:

输入在第一行给出正整数 N (≤105);随后一行给出{ 0, 1, 2, ..., N-1 } 的一个排列。数字间以空格分隔。

输出格式:

在一行中输出将给定序列进行增序排序所需要的最少的与 0 交换的次数。

输入样例:

10
3 5 7 2 6 4 9 0 8 1

输出样例:

9

 

#include<iostream>
#include<map> // 这里为了方便就直接用map了,实际可以全部用数组
using namespace std;
int main()
{
    long N,num[100001],sum=0;
    map<long,long> site;
    cin >> N;
    /*   数据读入并记入对应数组所在的下标   */
    for(long z=0;z<N;z++) {
        cin >> num[z];
        site[num[z]] = z;
    }
    /*   将0回归到0的位置   */
    while (site[0]!=0){
        sum++;
        num[site[0]] = site[0];
        site[0] = site[site[0]];
        site[num[site[0]]] = num[site[0]];
        num[site[0]] = 0;
    }
    /*   开始额外递归   */
    long f = 0;  // 记入需要额外增加的交换次数
    for(long z=1;z<N;z++)
    {
        if(num[z]!=z) // 这里每多递归一次需要额外交换两次
        {
            f+=2;
            while (site[z]!=z){
                sum++;
                long op = site[site[z]];  // 因为z回归过来的数不确定(上面是回归0是确定的),所以需要事先记入他下一个要回归的数
                num[site[z]] = site[z];
                site[z] = site[site[z]];
                site[num[site[z]]] = num[site[z]];
                num[site[z]] = z;
                z = op; // 判断是否刚好符号[0.2.1.3.4] 形式的交换(2和1刚好互相在对方的位置上)
            }
        }
    }
    cout << sum+f;
    return 0;
}

  • 3
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论
OpenCL(Open Computing Language)是一种开放的跨平台并行计算框架,它允许开发者在不同的硬件平台上进行并行计算。零拷贝(Zero-Copy)是OpenCL中的一种技术,用于在主机(CPU)和设备(GPU)之间实现数据的高效传输。 在传统的计算模型中,主机和设备之间的数据传输通常需要通过主机内存进行拷贝,这会导致额外的内存开销和数据传输延迟。而零拷贝技术通过共享主机内存和设备内存的方式,避免了数据的多次拷贝,提高了数据传输的效率。 在OpenCL中,可以使用零拷贝技术通过以下步骤实现数据的高效传输: 1. 创建共享内存缓冲区:在主机端创建一个共享内存缓冲区,并将其映射到设备端。 2. 分配设备端内存:在设备端分配一块内存,用于与共享内存缓冲区进行数据交换。 3. 将数据写入共享内存缓冲区:将需要传输的数据写入共享内存缓冲区。 4. 在设备端进行计算:使用OpenCL在设备端进行并行计算,可以直接访问共享内存缓冲区中的数据。 5. 将计算结果读取到共享内存缓冲区:将设备端计算得到的结果写入共享内存缓冲区。 6. 从共享内存缓冲区读取数据:将最终的计算结果从共享内存缓冲区读取到主机端。 通过使用零拷贝技术,可以减少数据传输的开销,提高计算效率。然而,零拷贝也有一些限制和注意事项,例如需要确保主机和设备端的内存访问一致性,并且在数据传输过程中需要进行同步操作。

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

三块不一样的石头

十分满意,一分打赏~

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值