ICode9

精准搜索请尝试: 精确搜索
首页 > 其他分享> 文章详细

dp(过河问题)

2019-08-09 21:04:24  阅读:261  来源: 互联网

标签:过河 seconds 问题 num members team corner include dp


http://codeforces.com/gym/101492/problem/E

Teamwork is highly valued in the ACM ICPC. Since the beginning, the ICPC has distinguished itself from other programming contests in that teamwork is a key factor.

The University of Beijing, host of next year's World Finals, is planning recreational activities for the participants. They want to prepare games that show the importance of teamwork and enable new acquaintances among the contestants from all over the world. One of the staff members has been thinking about the following game.

In a court we have several N-person teams. The goal of each team is roughly as follows: starting from a corner, each team must take all of its members to the other corner of the court. The winning team is the one that finishes this in the shortest time.

Now we explain the game more formally. Consider the team that starts at corner A and must take all of its members to corner B. The following procedure is repeated:

  1. While there are team members at corner A,
    • If there is only one team member, he is the only one that goes to corner B.
    • Otherwise, two team members must tie one leg of each with a rope and go to B.
  2. Once arriving at B, they untie their legs, if applicable.
  3. If there are still team members at corner A, some team member at B must return to A with the rope.

The organization wants to form the teams so that no team has an advantage. They entrusted you with the following task. Given the time in seconds that the members of a team take to go from a corner to the other, find the minimum time it takes for the team to take all its members from corner A to corner B. When two team members cross the court with their legs tied, the time for the pair to cross is the maximum between the times of the two members.


Input

The first line of input contains an integer N, the number of team members. The next line contains N integers ti, the time in seconds that the i-th team member takes to go from one corner to the other.

  • 1 ≤ N ≤ 105
  • 1 ≤ ti ≤ 109
Output

Print a single integer, the minimum time required for the whole team to reach corner B.

Examples Input
3
30 40 50
Output
120
Input
4
10 20 50 100
Output
170
Note

In the first example, the process can be completed in 120 seconds as follows:

  1. The first and second members go from A to B in 40 seconds.
  2. The first member returns to corner A in 30 seconds.
  3. The first and third team members go from A to B in 50 seconds.

This is not the only way to complete the process in this total time, but no other way does it in strictly less than 120 seconds.

思路:

按过河时间排序后

有两种最优策略:

1.最轻的带最重的过去,

2.两个最轻的带两个最重的过去。

每次判断两人,比较两种策略哪个更优。

样例1:编号为1,2,3,首先1和3先过去,1回来,然后1和2过去,时间是50+30+40=120

样例2:编号为1,2,3,4,首先1和2先过去,1回来,然后3和4过去,2回来,最后1和2过去,时间是20+10+100+20+20=170

题目分析:这题看起来似乎是dp的题目,但是看内存和时间,2个循环的时间并不足够。但是稍微分析,其实可以发现,有两种情况:

假设有编号为1,2,3,4,4个人在A要去B;

第一种情况:先1+2过去,然后换3+4过去;具体流程是1+2过去,1回来,3+4过去,2回来,此时时间是t1=num[2]+num[1]+num[4]+num[2]=num[2]*2+num[1]+num[4];

第二种情况:1+4过去,1回来,1+3过去,1回来;也就是通过1来回,逐个过去。时间是t2=num[4]+num[1]+num[3]+num[1]=num[1]*2+num[3]+num[4];

由上两种情况,总结出选择哪一种过法,可以比较t1和t2的时间取小,也就是看num[2]+num[2]>num[1]+num[3]?t1:t2

#include <cmath>
#include <algorithm>
#include <iostream>
#include <algorithm>
#include <iostream>
#include <cstdio>
#include <string>
#include <cstring>
#include <stdio.h>
#include <set>
#include <stack>
#include <string.h>
#include <vector>
#include <queue>
#define ME(x , y) memset(x , y , sizeof(x))
#define SF(n) scanf("%d" , &n)
#define rep(i , n) for(int i = 0 ; i < n ; i ++)
#define INF  0x3f3f3f3f
using namespace std;
long long a[100009];

int main()
{
    int n ;
    while(scanf("%d" , &n) != EOF)
    {
        for(int i = 0 ; i < n ; i++)
        {
            scanf("%lld" , &a[i]);
        }
        sort(a , a + n);
        long long ans = 0 ;
        if(n == 1)
        {
            ans = a[0];
        }
        else
        {
            if(n % 2 == 1)
            {
                ans += a[0] + a[1] + a[2];
                for(int i = 4 ; i < n ; i += 2)
                {
                    ans += min(2 *a[0] + a[i-1] + a[i] , a[0] + 2*a[1] + a[i]);
                }
            }
            else
            {
                ans += a[1];
                for(int i = 3 ; i < n ; i += 2 )
                {
                    ans += min(2*a[0] + a[i-1] + a[i] , a[0] + 2*a[1] + a[i]);
                }
            }
        }
        printf("%lld\n" , ans);

    }



    return 0 ;
}

 

标签:过河,seconds,问题,num,members,team,corner,include,dp
来源: https://www.cnblogs.com/nonames/p/11329547.html

本站声明: 1. iCode9 技术分享网(下文简称本站)提供的所有内容,仅供技术学习、探讨和分享;
2. 关于本站的所有留言、评论、转载及引用,纯属内容发起人的个人观点,与本站观点和立场无关;
3. 关于本站的所有言论和文字,纯属内容发起人的个人观点,与本站观点和立场无关;
4. 本站文章均是网友提供,不完全保证技术分享内容的完整性、准确性、时效性、风险性和版权归属;如您发现该文章侵犯了您的权益,可联系我们第一时间进行删除;
5. 本站为非盈利性的个人网站,所有内容不会用来进行牟利,也不会利用任何形式的广告来间接获益,纯粹是为了广大技术爱好者提供技术内容和技术思想的分享性交流网站。

专注分享技术,共同学习,共同进步。侵权联系[81616952@qq.com]

Copyright (C)ICode9.com, All Rights Reserved.

ICode9版权所有