题目
给定T组数据,每组数据n组值,选定合理序列使
最小
其中,特别的
数据范围:
贪心策略
易知严格递增,故
假设前n项已经为最优序列,考虑新加入元素
观察结构可知,调换相邻两项不影响最前面已经排好的序列的值
考虑与
两个序列的
两值
记
(最后一行应该是
)
由此不等式可以看出问题可能具有最优子结构,且可以直接进行贪心的选择
注意:不可直接用等式进行排序,该不等式不具有传递性,也就是说直接排序后序列不一定最优
2
7
6 3
1 1
7 3
1 1
1 6
1 1
6 10
7
6 10
1 1
6 3
1 1
7 3
1 1
1 6
(一组hack数据)
分析上述式的结构,可以看出不等式与
值的正负密切相关,这里引入
1°对于值相等的集合中,不等式存在明显的传递性
2°若,不妨
, 则
上述
成立
3°故可先对值不同进行分类,在对相等的值进行排序
#include <cstdio>
#include <iostream>
#include <algorithm>
#include <cstring>
using namespace std;
using LL = long long;
int T, N;
struct node {
LL a, b, c, d;
} p[20005];
LL pre[20005];
int sgn(int);
bool cmp(node, node);
LL ans;
int main(){
ios::sync_with_stdio(false);
cin >> T;
while(T--){
cin >> N;
int i;
for(i = 1; i <= N; i++)
cin >> p[i].a >> p[i].b, p[i].d = sgn(p[i].a - p[i].b);
sort(p + 1, p + 1 + N, cmp);
for(i = 1; i <= N; i++) pre[i] = pre[i - 1] + p[i].a;
for(i = 1; i <= N; i++)
p[i].c = max(p[i - 1].c, pre[i]) + p[i].b;
cout << p[N].c << endl;
}
return 0;
}
int sgn(int x){
if(!x) return x;
return (x > 0) ? 1 : -1;
}
bool cmp(node x, node y){
if(x.d != y.d) return x.d < y.d;
if(x.d <= 0) return x.a < y.a;
else return y.b < x.b;
}