poj 1062 昂贵的聘礼

昂贵的聘礼

这道题我用的深搜加剪枝做的,注意点就是判断等级那块,一路换下来,不能出现等级差大于等级限制的,比如等级限制为1,前面跟4级的交易了,就再也不能和小于三级的交易,反过来也是一样的,题意里这点描述有点矛盾。还有就是注意一定剪枝,不然会超时的,如果到某一个人那发现交易过了,要比较交易完剩下的钱,如果剩的少说明现在没有原来的更划算,所以就不用继续交易了,这样省了很多不必要的情况,同时也避免了环。

#include<cstdio>
#include<cstring>
#include<algorithm>
#define N 102
#define M 0xfffffff
using namespace std;
int m,n,p,l,x,t,v,minpr;
int pr[N],val[N],rank[N],map[N][N];
int minval[N];
bool vis[N];

bool rankok(int i,int minl,int maxl)
{
    if((i<minl && maxl-i>m) ||(i>maxl && i-minl>m))
        return 0;
    else
        return 1;
}

void dfs(int I,int minl,int maxl)
{
    int i,j;
    for(j=1; j<=n; j++)
    {
        if(map[I][j]!=-1&&rankok(rank[j],minl,maxl)&&vis[j]==0)
        {
            if(val[j]<val[I]-map[I][j]+pr[j])
                continue;
            vis[j]=1;
            val[j]=val[I]-map[I][j]+pr[j];
            if(minpr>val[j])
                minpr=val[j];
            dfs(j,min(minl,rank[j]),max(maxl,rank[j]));
            vis[j]=0;
        }
    }
    return;
}

int main()
{
    int i,j;
    memset(vis,0,sizeof(vis));
    memset(map,-1,sizeof(map));
    memset(minval,-1,sizeof(minval));
    for(i=0; i<N; i++)
        val[i]=M;

    scanf("%d%d",&m,&n);
    for(i=1; i<=n; i++)
    {
        scanf("%d%d%d",&p,&l,&x);
        pr[i]=p;
        rank[i]=l;
        for(j=1; j<=x; j++)
        {
            scanf("%d%d",&t,&v);
            map[i][t]=p-v;
        }
    }
    minpr=val[1]=pr[1];
    vis[1]=1;
    dfs(1,rank[1],rank[1]);
    printf("%d\n",minpr);
    return 0;
}

/**
1 4
10000 4 2
2 8000
3 5000
1000 2 1
4 200
3000 2 1
4 200
50 2 0
*/
/*
<pre>100 13
10000 1 13
1 1
2 2
3 3
4 4
5 5
6 6
7 7
8 8
9 9
10 10
11 11
12 12
13 13
10000 1 13
1 1
2 2
3 3
4 4
5 5
6 6
7 7
8 8
9 9
10 10
11 11
12 12
13 13
10000 1 13
1 1
2 2
3 3
4 4
5 5
6 6
7 7
8 8
9 9
10 10
11 11
12 12
13 13
10000 1 13
1 1
2 2
3 3
4 4
5 5
6 6
7 7
8 8
9 9
10 10
11 11
12 12
13 13
10000 1 13
1 1
2 2
3 3
4 4
5 5
6 6
7 7
8 8
9 9
10 10
11 11
12 12
13 13
10000 1 13
1 1
2 2
3 3
4 4
5 5
6 6
7 7
8 8
9 9
10 10
11 11
12 12
13 13
10000 1 13
1 1
2 2
3 3
4 4
5 5
6 6
7 7
8 8
9 9
10 10
11 11
12 12
13 13
10000 1 13
1 1
2 2
3 3
4 4
5 5
6 6
7 7
8 8
9 9
10 10
11 11
12 12
13 13
10000 1 13
1 1
2 2
3 3
4 4
5 5
6 6
7 7
8 8
9 9
10 10
11 11
12 12
13 13
10000 1 13
1 1
2 2
3 3
4 4
5 5
6 6
7 7
8 8
9 9
10 10
11 11
12 12
13 13
10000 1 13
1 1
2 2
3 3
4 4
5 5
6 6
7 7
8 8
9 9
10 10
11 11
12 12
13 13
10000 1 13
1 1
2 2
3 3
4 4
5 5
6 6
7 7
8 8
9 9
10 10
11 11
12 12
13 13
10000 1 13
1 1
2 2
3 3
4 4
5 5
6 6
7 7
8 8
9 9
10 10
11 11
12 12
13 13
*/
//这是讨论里的几组数据
 


评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值