제출 #940255

#제출 시각아이디문제언어결과실행 시간메모리
940255daoda은행 (IZhO14_bank)C++17
100 / 100
97 ms16852 KiB
#include <iostream>
#include <vector>
#include <algorithm>
#include <set>
#include <map>
#include <queue>
#include <cmath>
#include <cstring>
#include <iomanip>
#include <numeric>

#define fast ios_base::sync_with_stdio(0); cin.tie(0); cout.tie(0);
#define FOR(a, b) for(ll i=a; i < (ll) b; i++)
#define endl '\n'
#define MOD 1000000007
#define TESTCASE ll t; cin >> t; for(ll T=0; T < t; T++)

using namespace std;

typedef long long int ll;
typedef vector<ll> vll;
typedef pair<ll,ll> pll;
typedef vector<pll> vpll;
typedef vector<bool> vb;
typedef vector<char> vc;
typedef vector<int> vi;
typedef pair<int, int> pi;
typedef vector<pi> vpi;

const ll INF = (ll) 1e18;
const ll INIT = 7;
const ll MAX_VAL = (ll) 34;
const ll MAX_SZ = (ll) 2e5;
const ll MULT = (ll) 1e11;
const double eps = 1e-5;

vi rd = {0, 0 , 1, -1}, cd = {1, -1, 0 , 0};


int main() { 
    fast

    // freopen("bank.in", "r", stdin);
    // freopen("bank.out", "w", stdout);
    
    // TESTCASE {
        
    // }

    ll n,m;
    cin >> n >> m;

    vll salaries(n + 1), notes(m + 1), pref_sal(m + 1, 0);

    FOR(1, n + 1) {
        cin >> salaries[i];

        pref_sal[i] = salaries[i];
        pref_sal[i] += pref_sal[i - 1];
    }
    FOR(1, m + 1) {
        cin >> notes[i];
    }

    ll subsets = (1 << m) - 1; 

    vpll dp(subsets + 1, make_pair(0, 0));

    //.first tracks the number of salaries that are paid, .second tracks the current sum of banknotes

    ll largest=0;

    for(ll cur_subset = 1; cur_subset <= subsets; cur_subset++) {
        for(ll bit=1; bit <= m; bit++) {
            if(cur_subset & (1 << (bit - 1))) {
                ll without = cur_subset ^ (1 << (bit - 1)); 

                dp[cur_subset].second = dp[without].second + notes[bit];
                dp[cur_subset].first = max(dp[cur_subset].first , dp[without].first + (dp[cur_subset].second - pref_sal[dp[without].first] == salaries[dp[without].first + 1]));

                largest = max(largest, dp[cur_subset].first);

                // cout << cur_subset << " " << bit << " " << dp[cur_subset].first << endl;

                if(largest == n) {
                    cout << "YES";
                    return 0;
                }
            }
        }
    }

    cout << "NO";
  
    return 0;
} 

/*

let dp[i] be the maximum number of salaries from the start which have been fulfilled using the subset i

transitions :

dp[a] = max(dp[a without element j] + (sum of all b[i] where i is in a - b[dp[a without element j]] == 0))

011111

*/
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...
#Verdict Execution timeMemoryGrader output
Fetching results...