제출 #1304351

#제출 시각아이디문제언어결과실행 시간메모리
1304351Euclid73은행 (IZhO14_bank)C++20
71 / 100
1096 ms9180 KiB
#include <bits/stdc++.h>
using namespace std;

#define ll long long

const ll MAXN=20;
const ll MAXM=20;

ll N, m;
vector<ll> allA, allB;

vector<bool> solveDp(vector<ll> a, vector<ll> b)
{
    ll n=a.size();
    vector<vector<bool>> dp(2);
    vector<ll> s(1<<m, 0);
    dp[0].resize(1<<m, 0);
    dp[1].resize(1<<m, 0);
    for (int i=0; i<(1<<m); i++)
    {
        for (int j=0; j<m; j++)
        {
            if (i & (1<<j))
            {
                s[i]+=b[j];
            }
        }
    }
    dp[0][0]=1;
    for (int i=0; i<n; i++)
    {
        for (int j=0; j<(1<<m); j++)
        {
            dp[(i+1)%2][j]=0;
        }
        for (int cur = 0; cur < (1 << m); cur++)
        {
            if (dp[i%2][cur]==0)
            {
                continue;
            }
            ll mask=(1<<m)-1-cur;
            for (int submask = mask; submask >= 0; submask = (submask - 1) & mask)
            {
                int subset = mask ^ submask;
                if (s[subset]==a[i])
                {
                    dp[(i+1)%2][cur+subset]=1;
                }
                if (submask==0)
                {
                    break;
                }
            }
        }
    }
    vector<bool> ans(1<<m);
    for (int i=0; i<(1<<m); i++)
    {
        ans[i]=dp[n%2][i];
    }
    return ans;
}

int main()
{
    ios_base::sync_with_stdio(false);
    cin.tie(0);
    cin >> N >> m;
    allA.resize(N);
    for (int i=0; i<N; i++)
    {
        cin >> allA[i];
    }
    allB.resize(m);
    for (int i=0; i<m; i++)
    {
        cin >> allB[i];
    }
    vector<ll> a1, a2;
    for (int i=0; i<N/2; i++)
    {
        a1.push_back(allA[i]);
    }
    for (int i=N/2; i<N; i++)
    {
        a2.push_back(allA[i]);
    }
    vector<bool> dp1=solveDp(a1, allB), dp2=solveDp(a2, allB);
    for (int i=0; i<(1<<m); i++)
    {
        if (!dp1[i])
        {
            continue;
        }
        for (int j=0; j<m; j++)
        {
            if (i & (1<<j))
            {
                continue;
            }
            dp1[i+(1<<j)]=1;
        }
        if (dp2[(1<<m)-1-i])
        {
            cout << "YES\n";
            return 0;
        }
    }
    cout << "NO\n";
}
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...