球染色
时间限制: 2 Sec 内存限制: 512 MB提交: 66 解决: 22
[ 提交][ 状态][ 讨论版]
题目描述
你需要对每组球染色,一个染成红色,一个染成蓝色。
Rmax, Rmin, Bmax, Bmin分别表示红色的球中权值最大的,红色的球中权值最小的,
蓝色的球中权值最大的,蓝色的球中权值最小的。
你的目标是最小化(Rmax − Rmin) × (Bmax − Bmin),输出这个值。
输入
接下来n行每行两个整数xi, yi。
输出
样例输入
2
3 7
2 5
样例输出
2
提示
第一组球中权值为3的球染成红色,权值为7的球染成蓝色。
第二组球中权值为2的球染成红色,权值为5的球染成蓝色。
(Rmax − Rmin) × (Bmax − Bmin) = (3 − 2) × (7 − 5) = 2
对于前10%的数据:n ≤ 20
对于前20%的数据:n ≤ 50
对于前40%的数据:n ≤ 200
对于前70%的数据:n ≤ 2000
对于所有数据:
1 ≤ n ≤ 105,1 ≤ xi, yi ≤ 109
·思路
起初只考虑到其中一个情况,
(Rmax − Rmin) × (Bmax − Bmin)
情况一: 最大与最小不在一边
假如 Rmin 是所有中最小的, Bmax 是所有中最大的。
这样的话只需要让Rmax 尽可能小, Bmin 尽可能大
操作便是 min(x,y)给R, max(x,y)给 B
然后只能过一半数据。 遇到
1 2
3 4 就GG 了 答案应该是 3 而不是 4
情况二: 最大与最小的在一边:
这个情况下贪心 比较麻烦, 贪心的操作是 假设 最大最小都在 B 这边
枚举 R, 把 x,y 互换 然后 维护 差值最小; 这样的操作目的是 在不破坏最大最小的
之间 尽可能使 另一边差值 最小
·具体操作 可以利用 multiset 容器,自带排序,还可以存在相同值, set 是单纯集合
注意 反向迭代器 rbegin() rend() begin() end() 是指针
begin() 是最小元素, end()是最大元素的下一个
rbegin() 是最大元素,rend()是最小元素的前一个
·代码实现:
#include <iostream>
#include <bits/stdc++.h>
#include <string.h>
#define mem(a,b) memset(a,b,sizeof(a))
using namespace std;
const int MOD=1e9+7;
typedef long long ll;
const int MAXN=1e5+15;
const ll INF=0x3f3f3f3f;
typedef pair<ll,ll>PA;
inline ll qpow(ll x,ll n){ll res=1;for(;n;n>>=1){if(n&1)res=(res*x);x=(x*x);}return res;}
pair<ll,ll>P;
vector<PA> V;
multiset<ll>R,B;
int cmp(PA a,PA b)
{
return a.first<b.first;
}
int main()
{
int n;
ll x,y;
ll res2,ans;
cin>>n;
for(int i=1;i<=n;i++)
{
cin>>x>>y;
V.push_back(make_pair(min(x,y),max(x,y)));
R.insert(min(x,y));
B.insert(max(x,y));
}
ll maR=-INF,maB=-INF;
ll miR=INF,miB=INF;
int col_max=0,col_min=0;
sort(V.begin(),V.end(),cmp);
for(int i=0;i<V.size();i++)
{
maR=max(V[i].first,maR);
maB=max(V[i].second,maB);
miR=min(V[i].first,miR);
miB=min(V[i].second,miB);
}
ans=(maR-miR)*(maB-miB);
//cout<<ans<<endl;
for(int i=0;i<V.size();i++)
{
R.erase(R.find(V[i].first));
B.insert(V[i].first);
//swap
B.erase(B.find(V[i].second));
R.insert(V[i].second);
//cout<<( *R.rbegin()-*R.begin() )<<" "<<( *B.rbegin()-*B.begin())<<endl;
ans= min (ans,( *R.rbegin()-*R.begin() )*( *B.rbegin()-*B.begin()) );
}
cout<<ans<<endl;
return 0;
}
123