• [51Nod1125] 交换机器的最小代价


    题意:N个高度不一的机器,排成一列,为了把他们排成高度递增的一列,每次可以交换两个机器,代价为两个机器的和

    题解:

    贪心+置换

    1、用每个置换内部的最小值交换置换长度减一次,其他点交换一次

    2、引入外部的最小点,交换它与内部最小点的位置,交换置换长度+2次后再把内部最小点换回来,其他点交换一次

    #include<iostream>
    #include<cstdio>
    #include<cstdlib>
    #include<cstring>
    #include<algorithm>
    #include<cmath>
    #define ll long long
    using namespace std;
    
    const int N = 50010;
    
    int Mi;
    bool vis[N];
    
    struct Node {
      int v,p;
      bool operator < (const Node &x) const {
        return v<x.v;
      }
    }a[N];
    
    int gi() {
      int x=0,o=1; char ch=getchar();
      while(ch!='-' && (ch<'0' || ch>'9')) ch=getchar();
      if(ch=='-') o=-1,ch=getchar();
      while(ch>='0' && ch<='9') x=x*10+ch-'0',ch=getchar();
      return o*x;
    }
    
    ll solve(int i) {
      int mi=a[i].v,j=a[i].p,cnt=0;
      ll ret=a[i].v;
      vis[i]=1;
      while(j!=i) {
        vis[j]=1;
        ret+=a[j].v;
        mi=min(mi,a[j].v);
        j=a[j].p;
        cnt++;
      }
      return ret+min(1ll*(cnt-1)*mi,1ll*(cnt+2)*Mi+mi);
    }
    
    int main() {
      int n=gi(); ll ans=0;
      for(int i=1; i<=n; i++) {
        a[i].v=gi();
        a[i].p=i;
      }
      sort(a+1,a+n+1);
      Mi=a[1].v;
      for(int i=1; i<=n; i++) {
        if(!vis[i]) ans+=solve(i);
      }
      printf("%lld", ans);
      return 0;
    }
    
  • 相关阅读:
    Microsoft.Office.Interop.Excel.Application同时存在于
    sql 判断是否为数字字符
    在res/drawable中的文件
    在res/values中的文件
    放在res/anim中的文件(持续更新)
    在res/xml中的文件
    资源种类
    在assets中的文件
    android讲义2之输入界面
    在res/menu中的文件
  • 原文地址:https://www.cnblogs.com/HLXZZ/p/7535750.html
Copyright © 2020-2023  润新知