博客园 首页 私信博主 显示目录 隐藏目录 管理

luogu P2507 [SCOI2008]配对

P2507 [SCOI2008]配对


题目背景

四川NOI2008省选


题目描述

你有 n 个整数Ai和n 个整数Bi。你需要把它们配对,即每个Ai恰好对应一个Bp[i]。要求所有配对的整数差的绝对值之和尽量小,但不允许两个相同的数配对。例如A={5,6,8},B={5,7,8},则最优配对方案是5ó8, 6ó5, 8ó7,配对整数的差的绝对值分别为2, 2, 1,和为5。注意,5ó5,6ó7,8ó8是不允许的,因为相同的数不许配对。


输入输出格式

输入格式:

第一行为一个正整数n,接下来是n 行,每行两个整数Ai和Bi,保证所有

Ai各不相同,Bi也各不相同。

输出格式:

输出一个整数,即配对整数的差的绝对值之和的最小值。如果无法配对,输

出-1。


输入输出样例

输入样例#1:
3
3 65
45 10
60 25
输出样例#1:
32
输入样例#2:
3
5 5
6 7
8 8
输出样例#2:
5

说明

30%的数据满足:n <= 104

100%的数据满足:1 <= n <= 105,Ai和Bi均为1到106之间的整数。


每个数最多和上3个数配成一组,贪心3个点就好

#include<iostream>
#include<cstdio>
#include<cstdlib>
#include<algorithm>
#define ll long long 
using namespace std;
const ll maxn=100000+999;
const ll INT=1e15+7;
ll read(){
    ll an=0,f=1;
    char ch=getchar();
    while(ch<'0'||ch>'9'){if(ch=='-')f=-1;ch=getchar();}
    while('0'<=ch&&ch<='9'){an=an*10+ch-'0';ch=getchar();}
    return an*f;
}
ll n;
ll a[maxn],b[maxn];
ll dp[maxn];
ll pd(ll i,ll j){
    if(a[i]==b[j])return INT;
    return abs(b[j]-a[i]);
}
int main(){
    n=read();
    for(ll i=1;i<=n;i++){
    a[i]=read();
    b[i]=read();
    }
    sort(a+1,a+1+n);
    sort(b+1,b+1+n);
    for(ll i=1;i<=n;i++)dp[i]=INT;
    for(ll i=1;i<=n;i++){
        if(i>=1)dp[i]=min(dp[i],dp[i-1]+pd(i,i));
        if(i>=2)dp[i]=min(dp[i],dp[i-2]+pd(i-1,i)+pd(i,i-1) );
        if(i>=3)dp[i]=min(dp[i],min(dp[i-3]+pd(i-2,i-1)+pd(i-1,i)+pd(i,i-2),dp[i-3]+pd(i-2,i)+pd(i-1,i-2)+pd(i,i-1)) );
    }
    cout<<dp[n];
    return 0;
}
s

by:s_a_b_e_r


同上,然而并不知道为什么qwq

看了dalao的博客讲解也没懂qwq

#include<iostream>
#include<cstdio>
#include<cmath>
#include<algorithm>
#define ll long long 
using namespace std;
const int N=100009;
const ll inf = (ll)(1e15);
ll n,a[N],b[N],f[N];
ll pd(int x,int y)
{
    if(a[x]==b[y])return inf;
    return abs(a[x]-b[y]);
}
int main()
{
    scanf("%d",&n);
    for(int i=1;i<=n;++i)scanf("%d%d",&a[i],&b[i]);
    sort(a+1,a+n+1);
    sort(b+1,b+n+1);
    f[0]=0;
    for(int i=1;i<=n;++i)
    {
        ll t=inf;
        if(i>=1)t=min(t,f[i-1]+pd(i,i));
        if(i>=2)t=min(t,f[i-2]+pd(i-1,i)+pd(i,i-1));
        if(i>=3)t=min(t,min(f[i-3]+pd(i,i-1)+pd(i-1,i-2)+pd(i-2,i),
                            f[i-3]+pd(i-2,i-1)+pd(i-1,i)+pd(i,i-2)));
         f[i]=t;
    }
    cout<<f[n]<<endl;
    return 0;
}
w

by:wypx


 

posted @ 2017-10-04 07:42  ck666  阅读(146)  评论(0编辑  收藏  举报