zoukankan      html  css  js  c++  java
  • Greedy --- HNU 13320 Please, go first

     Please, go first

    Problem's Link:  http://acm.hnu.cn/online/?action=problem&type=show&id=13320


     

    Mean: 

    n个人一起去滑雪,要坐电梯到山顶,电梯每5分钟可以送一个人上去。这n个人中有的是组好团一起滑雪的,所以要等到齐了才能开始滑。

    但是他们到达电梯下的时间都不是统一的,对于单独一个人来说,他在山下等和在山上等的时间都是一样的。

    但是对于n个人的集体来说,如果让他后面的人先上去,这样可能会更节省时间。

    求通过调整上电梯的顺序后最多可以节省多少时间。(PS:被这鬼题意坑死 ==||)

    analyse:

    典型的贪心题。

    首先我们来分析未调整之前的状态:

    对于一个人,不管你来得多早,你还是得等到和你一个团的最后来的那个人才能开始滑雪。

    这样时间浪费在哪里了呢?如果是这种情况:AABBBBBBBBBBBBBBABBB,如果我们变成AAABBBBBBBBBBBBBBBBB,

    虽然B团队的时间没变,但是对于A团队来说却节省了很多时间。要贪心的地方就在这。

    如何贪呢?

    首先需要明确的是:我们不能把同一个团中最后到的那个人提前(人都还没到怎么提),而只能把中间掺杂的其他团的人提前,

    而最优情况肯定是:让同一个团的尽量聚合在一起,这样等待的时间才是最少的。

    综合这两个条件,我们首先求出未调整队形之前的每种元素的最左边的的位置。

    然后按照这个数组来个字符串排序(1.同一个团队的人聚合在一起;2.不同团队之间按照最后的人位置来排序)。

    最后对于每个元素,我们求这个元素调整前和调整后的位置之差,累加,最后*5即得答案。

    Time complexity: O(N)

     

    Source code:

    /*
    * this code is made by crazyacking
    * Verdict: Accepted
    * Submission Date: 2015-07-26-22.01
    * Time: 0MS
    * Memory: 137KB
    */
    #include <queue>
    #include <cstdio>
    #include <set>
    #include <string>
    #include <stack>
    #include <cmath>
    #include <climits>
    #include <map>
    #include <cstdlib>
    #include <iostream>
    #include <vector>
    #include <algorithm>
    #include <cstring>
    #define  LL long long
    #define  ULL unsigned long long
    using namespace std;
    const int MAXN = 25010;
    char s[MAXN];
    int orp[125], nrp[125], t, n;
    bool cmp( char a, char b ) {return orp[a] < orp[b];}
    int main()
    {
         ios_base::sync_with_stdio( false );
         cin.tie( 0 );
         cin >> t;
         while( t-- )
         {
               cin >> n >> s;
               for( int i = 0; i < n; ++i ) orp[s[i]] = i;
               sort( s, s + n, cmp );
               for( int i = 0; i < n; ++i ) nrp[s[i]] = i;
               long long ans = 0;
               for( int i = 0; i < n; ++i ) ans += abs( orp[s[i]] - nrp[s[i]] );
               cout << ans * 5 << endl;
         }
         return 0;
    }
    /*

    */
  • 相关阅读:
    word-wrap与word-break为长单词换行
    background-origin与background-clip的“区别”
    box-shadow
    你不知道的border-radius
    当document.write 遇到外联script
    getAttribute()方法的第二个参数
    Backbone.js入门教程第二版笔记(3)
    Backbone.js入门教程第二版笔记(2)
    php中的字符串常用函数(二) substr() 截取字符串
    php中类和对象的操作
  • 原文地址:https://www.cnblogs.com/crazyacking/p/4678919.html
Copyright © 2011-2022 走看看