Fence Repair POJ - 3253 (贪心)
https://vjudge.net/problem/POJ-3253
白书上的一道贪心问题, 做法也是仿照书中的做法来做的
把切割方法模拟为一个二叉树, 用数组来模拟即可, 每次最短的两个点一定是兄弟节点, 注意对奇书版数的特判
//Fence Repair 贪心
#include<cstdio>
#include<iostream>
#include<algorithm>
#include<cstring>
#include <string>
#include <vector>
#include <queue>
using namespace std;
#define ms(x, n) memset(x,n,sizeof(n));
typedef long long ll;
const ll maxn = 20010;
int N, plank[maxn];
ll solve()
{
ll ans = 0;
//直到计算到模板为1块为止
while(N > 1){
int min1 = 0, min2 = 1; //最小的和其次小的
if(plank[min2] < plank[min1]) swap(min1, min2);
//找出每次最小的和其次小的
for(int i = 2; i < N; i++){
if(plank[i] < plank[min1]) min2 = min1, min1 = i;
else if(plank[i] < plank[min2]) min2 = i;
}
int t = plank[min1] + plank[min2];
ans += t;
if(min1 == N-1) swap(min1, min2); // 只剩一个的情况
plank[min1] = t, plank[min2] = plank[N-1]; //用数组模拟树的节点
N--;
}
return ans;
}
int main()
{
cin >> N;
for(int i = 0; i < N; i++)
cin >> plank[i];
printf("%lld\n",solve());
return 0;
}