146572025-01-25 17:13:45arnoldbeilandSzitakötő (50 pont)cpp17Elfogadva 50/5063ms4332 KiB
#include <iostream>
#include <fstream>
#include <vector>
using namespace std;

//ifstream fin("input.txt");
//ofstream fout("output.txt");
istream &fin = cin;
ostream &fout = cout;

long long mod = 1000*1000*1000+7;

long long megold_hatekony(int n, int k, const vector<long long> &meret);

int main()
{

    int n, k;
    fin >> n >> k;

    vector<long long> meret(n+1);
    for (int i = 1; i <= n; i++)
        fin >> meret[i];

    fout << megold_hatekony(n, k, meret) << "\n";


    return 0;
}

long long megold_hatekony(int n, int k, const vector<long long> &meret)
{
    vector<long long> pow2(n+1);
    pow2[0] = 1;
    for (int i = 1; i <= n; i++)
        pow2[i] = pow2[i-1]*2 % mod;

    vector<long long> sp(n+1, 0); // részösszegek a meret-en
    for (int i = 1; i <= n; i++)
        sp[i] = sp[i-1] + meret[i];

    long long szorzo_bal = 0;

    // k balra kell induljon ha nem utolso...

    for (int i = 0; i <= k-1; i++) {
        // i = hányan indulnak jobbra közvetlenül k előtt
        // a (k-i-1). már balra indul ha még létezik
        long long kmerete = sp[k] - sp[k-i-1];
        if (kmerete >= sp[k-i-1]) {
            long long lehetosegek_elotte = pow2[max(0, k-1 - i - 1)];
            szorzo_bal = (szorzo_bal + lehetosegek_elotte) % mod;
        }
    }

    /*
        i > k esetén legyen

        dp[i] = az i, i+1, ... n lárvák olyan indulási lehetőségeinek száma,
                melyekkel nem alakul ki sum(meret[1], meret[i-1])-nél
                nagyobb vagy egyenlő lárva (aki felfalná a balra levőket)

        dp[n+1] = 1
        dp[n] = {
            0, ha meret[n] >= sum(meret[1]...meret[n])
            2, különben (indulhat balra vagy jobbra is)
        }

        dp[i] = {
            0, ha meret[i] >= sum(meret[1]...meret[i-1])
            különben: sum(
                // i balra indul:
                dp[i+1],

                // i jobbra indul:
                sum(dp[x+1], minden x-re, ahol
                    i < x <= n és
                    sum(meret[i]...meret[x]) < sum(meret[1], meret[i-1])
                )
            )
        }
        = sum(dp[x+1], minden x-re, ahol
            i <= x <= n és
            sum(meret[i]...meret[x]) < sum(meret[1], meret[i-1])
        )

        dp kiszámolható O(N*log(N)) időben, ha minden i-re binárisan
        keressük a legnagyobb x-et és a dp tömbön is részösszegeket
        számolunk menet közben
    */

    if (k == n)
        return 2 * szorzo_bal % mod;

    if (meret[n] >= sp[n-1])
        return 0;


    vector<long long> dp(n+2);
    vector<long long> dps(n+3); // dps[i] = dp[i] + dp[i+1] + ... + dp[n+1]
    dps[n+2] = 0;
    dp[n+1] = 2;
    dps[n+1] = dp[n+1] + dps[n+2];
    dp[n] = 2;
    dps[n] = dp[n] + dps[n+1];

    for (int i = n-1; i > k; i--) {
        int xbal = i, xjobb = n;
        while (xbal < xjobb) {
            int mid = (xbal+xjobb+1)/2;
            if (sp[mid]-sp[i-1] < sp[i-1])
                xbal = mid;
            else
                xjobb = mid-1;
        }
        if (sp[xbal] - sp[i-1] < sp[i-1]) {
            dp[i] = dps[i+1] - dps[xbal+2]; /* dp[i+1] + ... + dp[x+1] */
            dp[i] = (dp[i]+mod)%mod;
        }
        else {
            //dp[i] = 0;
            return 0;
        }

        dps[i] = (dp[i] + dps[i+1]) % mod;
    }

    return (szorzo_bal * dp[k+1])%mod;
}

RészfeladatÖsszpontTesztVerdiktIdőMemória
base50/50
1Elfogadva0/01ms508 KiB
2Elfogadva0/063ms4272 KiB
3Elfogadva1/11ms500 KiB
4Elfogadva1/11ms316 KiB
5Elfogadva1/11ms548 KiB
6Elfogadva1/11ms316 KiB
7Elfogadva1/11ms316 KiB
8Elfogadva1/11ms316 KiB
9Elfogadva1/11ms512 KiB
10Elfogadva2/21ms316 KiB
11Elfogadva2/21ms384 KiB
12Elfogadva2/21ms316 KiB
13Elfogadva2/21ms316 KiB
14Elfogadva2/21ms352 KiB
15Elfogadva2/21ms316 KiB
16Elfogadva2/21ms316 KiB
17Elfogadva2/21ms316 KiB
18Elfogadva2/21ms316 KiB
19Elfogadva2/21ms316 KiB
20Elfogadva2/21ms316 KiB
21Elfogadva1/11ms316 KiB
22Elfogadva2/248ms4264 KiB
23Elfogadva2/248ms4228 KiB
24Elfogadva2/263ms4332 KiB
25Elfogadva2/257ms4120 KiB
26Elfogadva2/250ms2732 KiB
27Elfogadva2/234ms4272 KiB
28Elfogadva2/252ms4272 KiB
29Elfogadva2/241ms4148 KiB
30Elfogadva2/263ms4160 KiB
31Elfogadva2/248ms2612 KiB