POJ Cowing Sorting (置换群的贪心(不只是置换群内部的贪心,还要与整体的贪心进行比较))

来源:互联网 发布:工作流程优化建议 编辑:程序博客网 时间:2024/04/30 02:06

Cow Sorting
Time Limit: 2000MS Memory Limit: 65536KTotal Submissions: 4763 Accepted: 1737

Description

Farmer John's N (1 ≤ N ≤ 10,000) cows are lined up to be milked in the evening. Each cow has a unique "grumpiness" level in the range 1...100,000. Since grumpy cows are more likely to damage FJ's milking equipment, FJ would like to reorder the cows in line so they are lined up in increasing order of grumpiness. During this process, the places of any two cows (not necessarily adjacent) can be interchanged. Since grumpy cows are harder to move, it takes FJ a total ofX+Y units of time to exchange two cows whose grumpiness levels areX and Y.

Please help FJ calculate the minimal time required to reorder the cows.

Input

Line 1: A single integer: N.
Lines 2..N+1: Each line contains a single integer: line i+1 describes the grumpiness of cowi.

Output

Line 1: A single line with the minimal time required to reorder the cows in increasing order of grumpiness.

Sample Input

3231

Sample Output

7

Hint

2 3 1 : Initial order.
2 1 3 : After interchanging cows with grumpiness 3 and 1 (time=1+3=4).
1 2 3 : After interchanging cows with grumpiness 1 and 2 (time=2+1=3).

Source

USACO 2007 February Gold

解题思路:由起始位置和最终位置来确定各个置换群,然后就开始贪心了,置换群内部的大家很好贪,那最小的那个元素与其它元素依次交换就可得出置换群内的最优解


,一般的想法就是把置换群内部的最优解加在一块得到的直接当作整体的最优解,然而不是这样的,原因很简单。但是又很难想到,就是直接那整体的最小值,先把置换群中的最小值置换掉,然后履行原来最小值的职责。最后再换回来,这个解可能比原来的那个解更优,因此取两个解中的较小值统计即可。实际上如果最值是循环所包含的,可以不必在意,因为按照替换最小值的方法,要比原来的多了两步,那么肯定是原来的那个是最优解的。所以实现起来就变的很简单了!

/* * File:   main.cpp * Author: hit-acm * * Created on 2012年9月5日, 下午7:51 *//* * 置换群的贪心,贪的不够优秀!!! */#include <iostream>#include <cstring>#include <algorithm>#include <cstdio>#include <cmath>using namespace std;const int MAXN = 10010;int father[MAXN];int num[MAXN];int min_num[MAXN];int val[MAXN];int N;struct node {    int index;    int val;    bool operator<(const node & a)const {        return val < a.val;    }} cow[MAXN];void init() {    for (int i = 0; i < N; i++) {        father[i] = i;        num[i] = 1;        min_num[i] = cow[i].val;        val[i] = cow[i].val;    }}int find_ancest(int x) {    if (x == father[x]) return x;    return father[x] = find_ancest(father[x]);}void Union(int x, int y) {    int u = find_ancest(x);    int v = find_ancest(y);    if (u != v) {        father[u] = v;        num[v] += num[u];        val[v] += val[u];        min_num[v] = min(min_num[v], min_num[u]);    }}int main() {    while (scanf("%d", &N) != EOF) {        for (int i = 0; i < N; i++) {            scanf("%d", &cow[i].val);            cow[i].index = i;        }        init();        sort(cow, cow + N);        int minest = cow[0].val;        for (int i = 0; i < N; i++) {            Union(i, cow[i].index);        }        int ans = 0;        bool color[MAXN];        memset(color, false, sizeof (color));        for (int i = 0; i < N; i++) {            int u = find_ancest(i);            if (!color[u]) {                color[u] = true;                ans += min(val[u] + min_num[u] * (num[u] - 2), val[u] + (num[u] + 1) * minest + min_num[u]);            }        }        printf("%d\n", ans);    }    return 0;}


原创粉丝点击