[贪心算法]最小操作数

有趣的二进制

题目描述

最近北京大学药学院的小晨在计概课上学习到二进制之后对其产生了浓厚的兴趣,在每次操作仅能移动相邻的0和1的前提下,她想知道把一个二进制数转换成另一个二进制数的最小操作数。

关于输入

输入共三行:
第一行为一个整数n (0 < n <= 200),代表二进制数的位数
第二行为第一个二进制数的每一位
第三行为第二个二进制数的每一位

关于输出

输出将第一个二进制数转换为第二个二进制数的最少操作数,如果答案不存在,则输出-1

例子输入
7
1 1 0 1 0 0 1
0 1 1 0 0 1 1
例子输出
4
解题分析

要解决本题,即寻求最小操作数,则要先想想怎么才能够操作最少次数,不失一般性,我们从第一个输入的二进制数的第一位开始遍历,如果发现它与目标二进制数不一样,则我们直接从该位的下一位开始找起,找到与目标二进制数该位相同的数后,再从后往前依次交换到当前位置,然后继续重复该操作即可。为什么这样就最少了呢?其实不难想象,比如0 1 1 0 0 0 1和1 1 1 0 0 0 0,我们把最后一位1直接依次交换直到第一位,和我先把最近的1捞过来用,然后重复操作,次数是一致的。

代码实现
#include <bits/stdc++.h>
using namespace std;
int main(){
    int n; cin>>n;
    int a[n],b[n]; int countA=0,countB=0;
    for(int i=0;i<n;i++){
        cin>>a[i];
        if(a[i]) countA++;
    }
    for(int i=0;i<n;i++){
        cin>>b[i];
        if(b[i]) countB++;
    }
    if(countA!=countB){
        cout<<-1<<endl; return 0;
    }
    else{
        int count=0;
        for(int i=0;i<n;i++){
            if(a[i]!=b[i]){
                for(int j=i+1;j<n;j++){
                    if(a[j]==b[i]){
                        for(int k=j;k>=i+1;k--){
                            swap(a[k],a[k-1]);
                            count++;
                        }
                        break;
                    }
                }
            }
        }
        cout<<count<<endl;
    }
    return 0;
}

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值