1 solutions

  • 0
    @ 2025-5-15 9:53:39

    O(TNmax(v[i]))O(TNmax(v[i]))

    这个题最难的点在于想到b集合是属于a集合的,这里我们简单证明一下,如果x属于b集合,不属于a集合,那么x是可以由a凑出来的,同时所有的a都是可以由b凑出来的,那么相当于x可以由b中的其它元素凑出来,那么与b是最小集合矛盾,所以b中的元素一定是a中的元素.

    接下来我们从小到大排序所有面值,按照面值的大小从小到大排序,如果当前面值可以凑出来,那么我们就不选它,如果不能,那么后面的也一定凑不出来,所以我们一定会选。

    #include<bits/stdc++.h>
    using namespace std;
    const int N=110;
    const int M=25010;
    int f[M];
    int v[N];
    int main()
    {
        int t;
        cin>>t;
        while(t--)
        {
            memset(f,0,sizeof f); //清空数组
            memset(v,0,sizeof v);
            int n;
            cin>>n;
            for(int i=1;i<=n;i++) //获取每个货币的面值
            {
                cin>>v[i];
            }
            sort(v+1,v+1+n); //排序
            int V=v[n];
            int res=0; //最开始一个都没有
            f[0]=1; //0可以凑出来
            for(int i=1;i<=n;i++)
            {
                if(f[v[i]]) continue; //这个面值可以由其它数构造出来,就不用选了
                res++; //选择当前面积
                for(int j=v[i];j<=V;j++) //更新可以凑出来的面值
                {
                    f[j]=max(f[j],f[j-v[i]]);
                }
            }
            cout<<res<<endl;
        }
        return 0;
    }
    
    • 1

    Information

    ID
    1131
    Time
    1000ms
    Memory
    256MiB
    Difficulty
    7
    Tags
    # Submissions
    1
    Accepted
    1
    Uploaded By