N - Crossing River

A group of N people wishes to go across a river with only one boat, which can at most carry two persons. Therefore some sort of shuttle arrangement must be arranged in order to row the boat back and forth so that all people may cross. Each person has a different rowing speed; the speed of a couple is determined by the speed of the slower one. Your job is to determine a strategy that minimizes the time for these people to get across.

Input

The first line of the input contains a single integer T (1 <= T <= 20), the number of test cases. Then T cases follow. The first line of each case contains N, and the second line contains N integers giving the time for each people to cross the river. Each case is preceded by a blank line. There won’t be more than 1000 people and nobody takes more than 100 seconds to cross.

Output

For each test case, print a line containing the total number of seconds required for all the N people to cross the river.

Sample Input

1
4
1 2 5 10

Sample Output

17

题意描述:

有N个人过河,但是只有一条船,一次最多乘2个人,有很多种过河的方案,船必须来回往返。每个人划船的速度都不同,两个人划船的时候,总体速度取决于速度慢的那一个。找出一个N个人全部过河的时间最少的方案。

解题思路:

当n<3时:

  1. n=3,最快的和次快的过河,然后最快的将船划回来,再最快的和最慢的过河。sum = a[0] + a[1] + a[2];

  2. n=2,最快的和最慢的过河。sum = a[1];

  3. n=1,sum = a[0];

当n>3时:

假设n个人单独过河所需要的时间存储在数组中,将数组按升序排序。
先让最快的和次快的过河,然后让其中一个回来,再让最慢的跟次慢的过河,再让另一个的回来。
即:

  1. 最快的和次快的过河,然后最快的将船划回来,再次慢的和最慢的过河,然后次快的将船划回来。a[0]+2*a[1]+a[n-1]

  2. 最快的和最慢的过河,然后最快的将船划回来,再最快的和次慢的过河,然后最快的将船划回来。2*a[0]+a[n-2]+a[n-1]

这两种情况取较小的。
样例解释:1 2 5 10

1.(1,2)先过河    时间是2" 
2.(2)回来        时间是2"  
3.(5,10)过河     时间10"
4.(1)回来        时间1"  
5.(1,2)过河      时间2"    
总时间17"

代码:

#include<stdio.h>
#include<algorithm>
using namespace std;
int a[10000];
int main()
{
    
    
	int t, n, m, i, j;
	scanf("%d", &t);
	while (t--)
	{
    
    
		int sum = 0,sum1,sum2;
		scanf("%d", &n);
		for (i = 0; i < n; i++)
			scanf("%d", &a[i]);
		sort(a, a + n);
		for (i = n - 1; i > 2; i -= 2)
		{
    
    
			sum1= 2 * a[0] + a[i - 1] + a[i];
			sum2= a[0] + 2 * a[1] + a[i];
			sum+=min(sum1,sum2); 
		}	
		if (i == 2)
			sum += a[0] + a[1] + a[2];
		else
			if (i == 1) 
				sum += a[1];
			else
				sum += a[0];
		printf("%d\n", sum);

	}
	return  0;
}

猜你喜欢

转载自blog.csdn.net/weixin_46703995/article/details/112530863