Problem J: [POI2009]SLO

Time Limit: 30 Sec  Memory Limit: 162 MB
Submit: 622  Solved: 302
[Submit][Status][Discuss]

Description

对于一个1-N的排列(ai),每次你可以交换两个数ax与ay(x<>y),代价为W(ax)+W(ay) 若干次交换的代价为每次交换的代价之和。请问将(ai)变为(bi)所需的最小代价是多少。

Input

第一行N。第二行N个数表示wi。第三行N个数表示ai。第四行N个数表示bi。 2<=n<=1000000 100<=wi<=6500 1<=ai,bi<=n ai各不相等,bi各不相等 (ai)<>(bi) 样例中依次交换数字(2,5)(3,4)(1,5)

Output

一个数,最小代价。

Sample Input

6
2400 2000 1200 2400 1600 4000
1 4 5 3 6 2
5 3 2 4 6 1

Sample Output

11200

HINT

题解:想到置换,发现在一个循环中,我们尽量让每个点与权值小的进行交换,但是这样会是最优吗?

   显然不是,我们忽略一种情况,我们可以将另一个循环中的一个最小的值与一个循环的一个节点交换,

   然后重复上述操作,再将它换回原来循环来产生更优的解!

   细节见代码:

BZOJ1119

#include<iostream>
#include<algorithm>
#include<cstring>
#include<cstdio>
#include<cmath>
#define ll long long
#define inf 0x7fffffff
#define N 1000010
using namespace std;
int n;
ll v[N],minn=inf,a[N],ans;
int cnt[N];
bool vis[N];
ll read()
{
ll x=,f=; char ch;
while (ch=getchar(),ch<''||ch>'') if (ch=='-') f=-;
while (x=x*+ch-'',ch=getchar(),ch>=''&&ch<='');
return x*f;
}
int main()
{
n=read();
for (int i=; i<=n; i++) v[i]=read(),minn=min(minn,v[i]);
for (int i=; i<=n; i++) a[i]=read();
for (int i=; i<=n; i++) cnt[read()]=i;
for (int i=; i<=n; i++)
{
if (!vis[i])
{
ll t=,mn=inf,sum=; int j=i;
while (!vis[j])
{
vis[j]=; t++; sum+=v[a[j]]; mn=min(mn,v[a[j]]); j=cnt[a[j]];
}
if (t>=)
{
ll t1=sum+1ll*mn*(t-),t2=sum+mn+1ll*minn*(t+);
ans+=min(t1,t2);
}
}
}
printf("%lld\n",ans);
return ;
}

BZOJ1697

 #include<iostream>
#include<algorithm>
#include<cmath>
#include<cstring>
#include<cstdio>
#define ll long long
#define inf 0x7fffffff
#define N 100005
using namespace std;
struct point{
ll v,pos;
}tmp[N];
ll v[N],minn=inf,a[N],ans;
int cnt[N];
bool vis[N];
ll read()
{
ll x=,f=; char ch;
while (ch=getchar(),ch<''||ch>'') if (ch=='-') f=-;
while (x=x*+ch-'',ch=getchar(),ch>=''&&ch<='');
return x*f;
}
bool cmp(point a,point b){return a.v<b.v;
}
int main()
{
int n=read();
for (int i=; i<=n; i++) v[i]=tmp[i].v=read(),a[i]=tmp[i].pos=i,minn=min(minn,tmp[i].v);
sort(tmp+,tmp+n+,cmp);
for (int i=; i<=n; i++){cnt[tmp[i].pos]=i;}
for (int i=; i<=n; i++)
{
if (!vis[i])
{
ll t=,mn=inf,sum=; int j=i;
while (!vis[j])
{
vis[j]=; t++; sum+=v[a[j]]; mn=min(mn,v[a[j]]); j=cnt[a[j]];
}
if (t>=)
{
ll t1=sum+1ll*mn*(t-),t2=sum+mn+1ll*minn*(t+);
ans+=min(t1,t2);
}
}
}
printf("%lld\n",ans);
return ;
}

BZOJ1119[POI2009]SLO && BZOJ1697[Usaco2007 Feb]Cow Sorting牛排序的更多相关文章

  1. BZOJ1697: [Usaco2007 Feb]Cow Sorting牛排序

    1697: [Usaco2007 Feb]Cow Sorting牛排序 Time Limit: 5 Sec  Memory Limit: 64 MBSubmit: 387  Solved: 215[S ...

  2. [BZOJ1697][USACO2007 FEB]Cow Sorting牛排序:贪心+置换

    分析 一个月前做的一道题补一下题解,就简单写一写吧. 单独考虑每一个循环节,如果只进行内部的调整,最优方案显然是把最小的绕这个循环交换一圈. 但是借助全局最小值可能使答案更优,两种情况取个\(\max ...

  3. BZOJ_1697_[Usaco2007 Feb]Cow Sorting牛排序_贪心

    BZOJ_1697_[Usaco2007 Feb]Cow Sorting牛排序_贪心 Description 农夫JOHN准备把他的 N(1 <= N <= 10,000)头牛排队以便于行 ...

  4. 【BZOJ 1697】1697: [Usaco2007 Feb]Cow Sorting牛排序

    1697: [Usaco2007 Feb]Cow Sorting牛排序 Description 农夫JOHN准备把他的 N(1 <= N <= 10,000)头牛排队以便于行动.因为脾气大 ...

  5. bzoj1697:[Usaco2007 Feb]Cow Sorting牛排序 & bzoj1119:[POI2009]SLO

    思路:以bzoj1119为例,题目已经给出了置换,而每一次交换的代价是交换二者的权值之和,而置换一定是会产生一些环的,这样就可以只用环内某一个元素去置换而使得其余所有元素均在正确的位置上,显然要选择环 ...

  6. bzoj 1119 [POI2009]SLO && bzoj 1697 [Usaco2007 Feb]Cow Sorting牛排序——思路(置换)

    题目:https://www.lydsy.com/JudgeOnline/problem.php?id=1119 https://www.lydsy.com/JudgeOnline/problem.p ...

  7. P1697: [Usaco2007 Feb]Cow Sorting牛排序

    这是一道置换群的裸题=-=,先拿来试试手对着打,以后应该会更加熟练吧! ; var n,i,j,maxx,minx,now,len,cursum,tmin,sum:longint; p:array[. ...

  8. BZOJ 1697: [Usaco2007 Feb]Cow Sorting牛排序

    Description 农夫JOHN准备把他的 N(1 <= N <= 10,000)头牛排队以便于行动.因为脾气大的牛有可能会捣乱,JOHN想把牛按脾气的大小排序.每一头牛的脾气都是一个 ...

  9. 【BZOJ】1697: [Usaco2007 Feb]Cow Sorting牛排序(置换群)

    http://www.lydsy.com/JudgeOnline/problem.php?id=1697 置换群T_T_T_T_T_T_T 很久以前在黑书和白书都看过,,,但是看不懂... 然后找了本 ...

随机推荐

  1. arrayList里的快速失败

    快速失败是指某个线程在迭代集合类的时候,不允许其他线程修改该集合类的内容,这样迭代器迭代出来的结果就会不准确. 比如用iterator迭代collection的时候,iterator就是另外起的一个线 ...

  2. 使用NGUI进行类似Button的操作

    下面例子以Label和Sprite为例,进行说明如何在NGUI中对控件添加单击响应的事件方法. 首先在UIRoot下添加Label控件,然后Scene场景中右键Label-->Attach--& ...

  3. springframwork历史版本下载地址

    http://sourceforge.net/projects/springframework/files/springframework-2/

  4. 剑指offer 整数中1 出现的次数

    给定一个十进制正整数N,写下从1开始,到N的所有整数,然后数一下其中出现的所有"1"的个数. 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 1 ...

  5. zf-关于收费统计没出来监利县的问题

    这个问题一看就知道跟存储过程有关,所以我直接去后台实现类找到了这个的存储过程 存储过程里第一句就是quhua_code  从 select 开始 就是查询出 4个地方的名字 然后在把这查询出的数据给@ ...

  6. 转 ORACLE数据库它可以存储 中文 字节或字符

    一:因为ORACLE数据库它可以存储字节或字符,例如 CHAR(12 BYTE) CHAR(12 CHAR)的意义是不同的.一般来说默认是存储字节,你可以查看数据库参数NLS_LENGTH_SEMAN ...

  7. android脚步---设置layout隐藏属性

    设置layout的属性,应用到android view的setVisibility 有三个值 visibility  VISIBLE, INVISIBLE, GONE. 可见的     不可见的    ...

  8. 项目整体说明及WBS练习

    乐谱识别研究的意义 纸质乐谱向数字化乐谱的转换,是人类音乐活动与计算机音乐处理之间进行信息交流的必经之路.光学乐谱识别是将纸质乐谱扫描输入计算机后,对乐谱图像加以处理.识别.分析,最终获得乐谱的计算机 ...

  9. IMapControl3 Interface(1) Properties属性

    IMapControl3 Interface Provides access to members that control the MapControl. Note: the IMapControl ...

  10. 用free -m查看的结果:

    用free -m查看的结果: # free -m          total    used    free     shared buffers     cached Mem:           ...