hihocoder1386 Pick Your Players(dp)

题意:

你需要买一个足球队(11个球员),每个球员有位置、价值。花费,有以下限制:
位置分为前锋(1-3人)、中腰(2-5)、后卫(3-5)、守门员(1)
每个人有 value,总的 value 是每个人的value加起来 ,选一个队长,队长的加两次
每个人有个 cost,总花费不能超过给定值
求:最大的 value,相应的最小的 cost,相应的购买方案数(大于1e9输出1e9)
10组数据,500个候选人,value 和 cost:V and C (0 <= V <= 1000, 0 <= C <= 1000),花费上界:1000

思路:

考虑dp(i,cost,j,k,r,w)=(value,way)表示考虑前i个球员,

费用和为cost,选了j个前锋k个中腰r个后卫w个守门员这个状态,价值和是value,方案数是way。

然后按照dp字面意思转移就可以了。然后第一维的iii这里是为了看起来方便,其实是不用开的。
为了方便处理队长,把球员们按照价值从大到小排序,挑的第一个人当队长就可以了。

以上取自ICPCCAMP题解

然后我就照着写了一发,怎么调都wa,感觉对对的- -

先存着吧,等以后或许有题解了再对比一下

可以把set换成vector+bool矩阵少一个log复杂度~

有哪位聚聚看出来问题请通知我~感激不尽

/* ***********************************************
Author        :devil
************************************************ */
#include <cstdio>
#include <cstring>
#include <iostream>
#include <algorithm>
#include <vector>
#include <queue>
#include <set>
#include <stack>
#include <map>
#include <string>
#include <cmath>
#include <stdlib.h>
#define inf 0x3f3f3f3f
#define LL long long
#define rep(i,a,b) for(int i=a;i<=b;i++)
#define dep(i,a,b) for(int i=a;i>=b;i--)
#define ou(a) printf("%d\n",a)
#define pb push_back
#define mkp make_pair
template<class T>inline void rd(T &x)
{
    char c=getchar();
    x=0;
    while(!isdigit(c))c=getchar();
    while(isdigit(c))
    {
        x=x*10+c-‘0‘;
        c=getchar();
    }
}
#define IN freopen("in.txt","r",stdin);
#define OUT freopen("out.txt","w",stdout);
using namespace std;
const int mod=1e9;
const int N=1e3+10;
pair<int,LL> dp[N][4][6][6][2];
struct wq
{
    char s[12];
    int val,cost;
} a[510];
bool cmp(wq a,wq b)
{
    return a.val>b.val;
}
set<int>eg[1500];
int main()
{
    int t,n,all;
    rd(t);
    while(t--)
    {
        rd(n);
        rep(i,1,n) scanf("%s",a[i].s),rd(a[i].val),rd(a[i].cost);
        rd(all);
        sort(a+1,a+n+1,cmp);
        memset(dp,0,sizeof(dp));
        int ansval=0,anscost=0;
        rep(i,0,1400) eg[i].clear();
        LL anssum=0;
        rep(i,1,n)
        {
            if(a[i].s[0]==‘F‘)
            {
                dep(f,3,1)dep(m,5,0)dep(d,5,0)dep(g,1,0)
                {
                    int hs=(f-1)*100+m*10+d+g*1000;
                    if(f+m+d+g>11||eg[hs].size()==0) continue;
                    for(auto j:eg[hs])
                    {
                        int c=j+a[i].cost;
                        if(c>all) continue;
                        if(dp[c][f][m][d][g].first<dp[c-a[i].cost][f-1][m][d][g].first+a[i].val)
                        {
                            dp[c][f][m][d][g].first=dp[c-a[i].cost][f-1][m][d][g].first+a[i].val;
                            dp[c][f][m][d][g].second=dp[c-a[i].cost][f-1][m][d][g].second;
                            eg[hs+100].insert(c);
                        }
                        else if(dp[c][f][m][d][g].first==dp[c-a[i].cost][f-1][m][d][g].first+a[i].val)
                        {
                            dp[c][f][m][d][g].second+=dp[c-a[i].cost][f-1][m][d][g].second;
                            if(dp[c][f][m][d][g].second>mod) dp[c][f][m][d][g].second=mod;
                            eg[hs+100].insert(c);
                        }
                    }
                }
                if(a[i].val*2>dp[a[i].cost][1][0][0][0].first)
                {
                    dp[a[i].cost][1][0][0][0].first=a[i].val*2;
                    dp[a[i].cost][1][0][0][0].second=1;
                    eg[100].insert(a[i].cost);
                }
                else if(a[i].val*2==dp[a[i].cost][1][0][0][0].first)
                {
                    dp[a[i].cost][1][0][0][0].second++;
                    eg[100].insert(a[i].cost);
                }
            }
            else if(a[i].s[0]==‘M‘)
            {
                dep(m,5,1)dep(f,3,0)dep(d,5,0)dep(g,1,0)
                {
                    int hs=f*100+(m-1)*10+d+g*1000;
                    if(f+m+d+g>11||eg[hs].size()==0) continue;
                    for(auto j:eg[hs])
                    {
                        int c=j+a[i].cost;
                        if(c>all) continue;
                        if(dp[c][f][m][d][g].first<dp[c-a[i].cost][f][m-1][d][g].first+a[i].val)
                        {
                            dp[c][f][m][d][g].first=dp[c-a[i].cost][f][m-1][d][g].first+a[i].val;
                            dp[c][f][m][d][g].second=dp[c-a[i].cost][f][m-1][d][g].second;
                            eg[hs+10].insert(c);
                        }
                        else if(dp[c][f][m][d][g].first==dp[c-a[i].cost][f][m-1][d][g].first+a[i].val)
                        {
                            dp[c][f][m][d][g].second+=dp[c-a[i].cost][f][m-1][d][g].second;
                            if(dp[c][f][m][d][g].second>mod) dp[c][f][m][d][g].second=mod;
                            eg[hs+10].insert(c);
                        }
                    }
                }
                if(a[i].val*2>dp[a[i].cost][0][1][0][0].first)
                {
                    dp[a[i].cost][0][1][0][0].first=a[i].val*2;
                    dp[a[i].cost][0][1][0][0].second=1;
                    eg[10].insert(a[i].cost);
                }
                else if(a[i].val*2==dp[a[i].cost][0][1][0][0].first)
                {
                    dp[a[i].cost][0][1][0][0].second++;
                    eg[10].insert(a[i].cost);
                }
            }
            else if(a[i].s[0]==‘D‘)
            {
                dep(d,5,1)dep(f,3,0)dep(m,5,0)dep(g,1,0)
                {
                    int hs=f*100+m*10+d-1+g*1000;
                    if(f+m+d+g>11||eg[hs].size()==0) continue;
                    for(auto j:eg[hs])
                    {
                        int c=j+a[i].cost;
                        if(c>all) continue;
                        if(dp[c][f][m][d][g].first<dp[c-a[i].cost][f][m][d-1][g].first+a[i].val)
                        {
                            dp[c][f][m][d][g].first=dp[c-a[i].cost][f][m][d-1][g].first+a[i].val;
                            dp[c][f][m][d][g].second=dp[c-a[i].cost][f][m][d-1][g].second;
                            eg[hs+1].insert(c);
                        }
                        else if(dp[c][f][m][d][g].first==dp[c-a[i].cost][f][m][d-1][g].first+a[i].val)
                        {
                            dp[c][f][m][d][g].second+=dp[c-a[i].cost][f][m][d-1][g].second;
                            if(dp[c][f][m][d][g].second>mod) dp[c][f][m][d][g].second=mod;
                            eg[hs+1].insert(c);
                        }
                    }
                }
                if(a[i].val*2>dp[a[i].cost][0][0][1][0].first)
                {
                    dp[a[i].cost][0][0][1][0].first=a[i].val*2;
                    dp[a[i].cost][0][0][1][0].second=1;
                    eg[1].insert(a[i].cost);
                }
                else if(a[i].val*2==dp[a[i].cost][0][0][1][0].first)
                {
                    dp[a[i].cost][0][0][1][0].second++;
                    eg[1].insert(a[i].cost);
                }
            }
            else
            {
                dep(f,3,0)dep(m,5,0)dep(d,5,0)
                {
                    int hs=f*100+m*10+d;
                    if(f+m+d+1>11||eg[hs].size()==0) continue;
                    for(auto j:eg[hs])
                    {
                        int c=j+a[i].cost;
                        if(c>all) continue;
                        if(dp[c][f][m][d][1].first<dp[c-a[i].cost][f][m][d][0].first+a[i].val)
                        {
                            dp[c][f][m][d][1].first=dp[c-a[i].cost][f][m][d][0].first+a[i].val;
                            dp[c][f][m][d][1].second=dp[c-a[i].cost][f][m][d][0].second;
                            eg[hs+1000].insert(c);
                        }
                        else if(dp[c][f][m][d][1].first==dp[c-a[i].cost][f][m][d][0].first+a[i].val)
                        {
                            dp[c][f][m][d][1].second+=dp[c-a[i].cost][f][m][d][0].second;
                            if(dp[c][f][m][d][1].second>mod) dp[c][f][m][d][1].second=mod;
                            eg[hs+1000].insert(c);
                        }
                    }
                }
                if(a[i].val*2>dp[a[i].cost][0][0][0][1].first)
                {
                    dp[a[i].cost][0][0][0][1].first=a[i].val*2;
                    dp[a[i].cost][0][0][0][1].second=1;
                    eg[1000].insert(a[i].cost);
                }
                else if(a[i].val*2==dp[a[i].cost][0][0][0][1].first)
                {
                    dp[a[i].cost][0][0][0][1].second++;
                    eg[1000].insert(a[i].cost);
                }
            }
            //printf("%d\n",i);
            //rep(f,0,3)rep(m,0,5)rep(d,0,5)rep(g,0,1)rep(c,0,all) if(dp[c][f][m][d][g].second) printf("%d %c %d %d %d %d %d %d %lld\n",i,a[i].s[0],f,m,d,g,c,dp[c][f][m][d][g].first,dp[c][f][m][d][g].second);
            //system("pause");
        }
        rep(f,1,3)rep(m,2,5)rep(d,3,5)
        {
            if(f+m+d<10) continue;
            if(f+m+d>10) break;
            int hs=f*100+m*10+d+1000;
            //printf("%d %d\n",hs,eg[hs].size());
            if(!eg[hs].size()) continue;
            for(auto j:eg[hs])
            {
                int c=j;
                //printf("%d %d %lld\n",c,dp[c][f][m][d][1].first,dp[c][f][m][d][1].second);
                if(dp[c][f][m][d][1].first>ansval)
                {
                    ansval=dp[c][f][m][d][1].first;
                    anscost=c;
                    anssum=dp[c][f][m][d][1].second;
                }
                else if(dp[c][f][m][d][1].first==ansval)
                {
                    if(c<anscost)
                    {
                        anscost=c;
                        anssum=dp[c][f][m][d][1].second;
                    }
                    else if(c==anscost)
                    {
                        anssum+=dp[c][f][m][d][1].second;
                        if(anssum>mod) anssum=mod;
                    }
                }
            }
        }
        if(anssum>mod) anssum=mod;
        printf("%d %d %lld\n",ansval,anscost,anssum);
    }
    return 0;
}

时间: 2024-10-13 15:54:22

hihocoder1386 Pick Your Players(dp)的相关文章

hdu 5623 KK&#39;s Number(dp)

问题描述 我们可爱的KK有一个有趣的数学游戏:这个游戏需要两个人,有N\left(1\leq N\leq 5*{10}^{4} \right)N(1≤N≤5∗10?4??)个数,每次KK都会先拿数.每次可以拿任意多个数,直到NN个数被拿完.每次获得的得分为取的数中的最小值,KK和对手的策略都是尽可能使得自己的得分减去对手的得分更大.在这样的情况下,最终KK的得分减去对手的得分会是多少? 输入描述 第一行一个数T\left( 1\leq T\leq 10\right)T(1≤T≤10),表示数据组

Ural 1353 Milliard Vasya&#39;s Function(DP)

题目地址:Ural 1353 定义dp[i][j],表示当前位数为i位时,各位数和为j的个数. 对于第i位数来说,总可以看成在前i-1位后面加上一个0~9,所以状态转移方程就很容易出来了: dp[i][j]=dp[i][j]+dp[i][j-1]+dp[i][j-2]+.......+dp[i][j-9]: 最后统计即可. 代码如下: #include <iostream> #include <cstdio> #include <string> #include <

HDU 4908 (杭电 BC #3 1002题)BestCoder Sequence(DP)

题目地址:HDU 4908 这个题是从m开始,分别往前DP和往后DP,如果比m大,就比前面+1,反之-1.这样的话,为0的点就可以与m这个数匹配成一个子串,然后左边和右边的相反数的也可以互相匹配成一个子串,然后互相的乘积最后再加上就行了.因为加入最终两边的互相匹配了,那就说明左右两边一定是偶数个,加上m就一定是奇数个,这奇数个的问题就不用担心了. 代码如下: #include <iostream> #include <stdio.h> #include <string.h&g

Sicily 1146:Lenny&#39;s Lucky Lotto(dp)

题意:给出N,M,问有多少个长度为N的整数序列,满足所有数都在[1,M]内,并且每一个数至少是前一个数的两倍.例如给出N=4, M=10, 则有4个长度为4的整数序列满足条件: [1, 2, 4, 8], [1, 2, 4, 9], [1, 2, 4, 10], [1, 2, 5, 10] 分析:可用动态规划解题,假设dp[i][j],代表满足以整数i为尾数,长度为j的序列的个数(其中每一个数至少是前一个数的两倍).那么对于整数i,dp[i][j] 等于所有dp[k][j-1]的和,其中k满足:

UVA542 - France &#39;98(dp)

UVA542 - France '98(dp) 题目链接 题目大意:之前题目意思还以为看懂了,其实没看明白,它已经把各个选手分在各自所在的区域里面,这就意味着第一次的PK的分组已经确定,而且冠军必须是从两个左右分区出来的胜利者才有机会pk冠军. 解题思路:那么从1-16这个大的区间内诞生出来的冠军可能是来自左边,也可能是右边,然后再左边右边的子区间递归找出冠军.f[i][l][r]表示l-r这个区间的胜利者是i的概率,那么假设i在区间的最左边,f[i][l][r] = Sum(f[i][l][m

HDU 4968 Improving the GPA(dp)

HDU 4968 Improving the GPA 题目链接 dp,最大最小分别dp一次,dp[i][j]表示第i个人,还有j分的情况,分数可以减掉60最为状态 代码: #include <cstdio> #include <cstring> #include <algorithm> using namespace std; int t, avg, n; double dp1[15][405], dp2[15][405]; double get(int x) { if

URAL 1167. Bicolored Horses (DP)

题目链接 题意 :农夫每天都会放马出去,然后晚上把马赶入马厩,于是让马排成一行入马厩,但是不想马走更多的路,所以让前p1匹入第一个马厩,p2匹马入第二个马厩…………但是他不想让他的任何一个马厩空着,所有的马都必须入马厩.有两种颜色的马,如果 i 匹黑马与 j 匹白马同在一个马厩,不愉快系数是 i * j,总系数就是k个系数相加.让总系数最小. 思路 : dp[i][j] 代表的是前 i 个马厩放 j 匹马的最小不愉快系数值. 1 //1167 2 #include <cstdio> 3 #in

2014多校第七场1005 || HDU 4939 Stupid Tower Defense (DP)

题目链接 题意 :长度n单位,从头走到尾,经过每个单位长度需要花费t秒,有三种塔: 红塔 :经过该塔所在单位时,每秒会受到x点伤害. 绿塔 : 经过该塔所在单位之后的每个单位长度时每秒都会经受y点伤害. 蓝塔 : 经过该塔所在单位之后,再走每个单位长度的时候时间会变成t+z. 思路 : 官方题解 : 1 #include <cstdio> 2 #include <cstring> 3 #include <iostream> 4 #define LL long long

hdu4939 Stupid Tower Defense (DP)

2014多校7 第二水的题 4939 Stupid Tower Defense Time Limit: 12000/6000 MS (Java/Others)    Memory Limit: 131072/131072 K (Java/Others) Total Submission(s): 366    Accepted Submission(s): 88 Problem Description FSF is addicted to a stupid tower defense game.