OpenJudge(硬币)

链接:https://vjudge.net/problem/OpenJ_Bailian-4120
思路:首先分析,如果一种硬币必须,那么除开这种硬币,就没法达到预期x的值,所以想着遍历所有硬币,除开当前硬币进行dp,如果能得到最后x值则不是必须的,反之为必须的,这样的复杂度为O(mn^2),超时,及时加了优化也不行。后来发现,其实很多部分重新计算了,不如计算出每种钱j选法的次数g[j],如果g[x]=0,那么当前硬币就是必需的。这种方法的复杂度O(mn)
代码:

#include
#include
#include
using namespace std;

const int maxn = 201;
int a[maxn];
int f[10001];
int g[10001];
int n,x,t=0;
int b[maxn];

int main(){
    scanf("%d%d",&n,&x);
    memset(b,0,sizeof(b));
    for(int i=0;i=a[i];--j){
                    f[j] += f[j-a[i]];
                }
        }
    for(int i=0;i=0){
                g[j] = f[j] - g[j-a[i]];
            }
            else g[j] = f[j];
        }
        if(g[x]==0){
            b[i] = 1;
            t++;
        }
    }
    printf("%d\n",t);
    t = 0;
    for(int i=0;i

你可能感兴趣的:(OpenJudge(硬币))