#include <bits/stdc++.h> using namespace std; #define REP(i,a,b) for (int i = (a); i <= (b); ++i) #define REPD(i,a,b) for (int i = (a); i >= (b); --i) #define FORI(i,n) REP(i,1,n) #define FOR(i,n) REP(i,0,int(n)-1) #define mp make_pair #define pb push_back #define pii pair<int,int> #define vi vector<int> #define ll long long #define SZ(x) int((x).size()) #define DBG(v) cerr << #v << " = " << (v) << endl; #define FOREACH(i,t) for (typeof(t.begin()) i=t.begin(); i!=t.end(); i++) #define fi first #define se second const int mod = 1000000007; const int N = 300300; //const int M = 1<<3; const int M = 1<<19; /// input int n; int a[N], pref[N], dp[N]; /// ids pii prefs[N]; int ids[N]; int T[2][M*2+13]; void add(int t0, int pos, int val) { //cerr << "adding (" << t0 << ") at position " << pos << " value " << val << "\n"; pos += M; while (pos > 0) { T[t0][pos] += val; if (T[t0][pos] >= mod) T[t0][pos] -= mod; pos /= 2; } /*cerr << "T[" << t0 << "] ="; FOR(i,M*2) { if (__builtin_popcount(i) == 1) cerr << " |"; cerr << " " << T[t0][i]; } cerr << "\n";*/ } int get(int t0, int pos) { //cerr << "reading (" << t0 << ") on interval [0, " << pos << "] : "; pos += M; int ans = T[t0][pos]; while (pos > 1) { if ((pos & 1) == 1) { ans += T[t0][pos-1]; if (ans >= mod) ans -= mod; } pos /= 2; } //cerr << ans << "\n"; return ans; } int main() { /// read input scanf("%d", &n); FORI(i,n) scanf("%d", &a[i]); FORI(i,n) pref[i] = (pref[i-1] + a[i]) % mod; /// prepare ids FOR(i,n+1) prefs[i] = mp(pref[i], i); sort(prefs,prefs+n+1); FOR(i,n+1) { ids[prefs[i].se] = i; if (i>0 && prefs[i].fi==prefs[i-1].fi) ids[prefs[i].se] = ids[prefs[i-1].se]; } //FOR(i,n+1) cerr << "i = " << i << ", pref = " << pref[i] << ", id = " << ids[i] << "\n"; dp[0] = 1; add(0, 0, 1); FORI(i,n) { /*int tmp_dp = 0; FOR(j,i) { if (pref[j] <= pref[i]) { if (pref[i]%2 == pref[j]%2) tmp_dp += dp[j]; } else { if (pref[i]%2 != pref[j]%2) tmp_dp += dp[j]; } if (dp[i] >= mod) tmp_dp -= mod; }*/ dp[i] = (0LL + get(pref[i]%2, ids[i]) + get(1-pref[i]%2, n) - get(1-pref[i]%2, ids[i]) + mod) % mod; //cerr << "i = " << i << " : dp slow = " << tmp_dp << ", dp fast = " << dp[i] << "\n"; add(pref[i]%2, ids[i], dp[i]); } printf("%d\n", dp[n]); return 0; }
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 | #include <bits/stdc++.h> using namespace std; #define REP(i,a,b) for (int i = (a); i <= (b); ++i) #define REPD(i,a,b) for (int i = (a); i >= (b); --i) #define FORI(i,n) REP(i,1,n) #define FOR(i,n) REP(i,0,int(n)-1) #define mp make_pair #define pb push_back #define pii pair<int,int> #define vi vector<int> #define ll long long #define SZ(x) int((x).size()) #define DBG(v) cerr << #v << " = " << (v) << endl; #define FOREACH(i,t) for (typeof(t.begin()) i=t.begin(); i!=t.end(); i++) #define fi first #define se second const int mod = 1000000007; const int N = 300300; //const int M = 1<<3; const int M = 1<<19; /// input int n; int a[N], pref[N], dp[N]; /// ids pii prefs[N]; int ids[N]; int T[2][M*2+13]; void add(int t0, int pos, int val) { //cerr << "adding (" << t0 << ") at position " << pos << " value " << val << "\n"; pos += M; while (pos > 0) { T[t0][pos] += val; if (T[t0][pos] >= mod) T[t0][pos] -= mod; pos /= 2; } /*cerr << "T[" << t0 << "] ="; FOR(i,M*2) { if (__builtin_popcount(i) == 1) cerr << " |"; cerr << " " << T[t0][i]; } cerr << "\n";*/ } int get(int t0, int pos) { //cerr << "reading (" << t0 << ") on interval [0, " << pos << "] : "; pos += M; int ans = T[t0][pos]; while (pos > 1) { if ((pos & 1) == 1) { ans += T[t0][pos-1]; if (ans >= mod) ans -= mod; } pos /= 2; } //cerr << ans << "\n"; return ans; } int main() { /// read input scanf("%d", &n); FORI(i,n) scanf("%d", &a[i]); FORI(i,n) pref[i] = (pref[i-1] + a[i]) % mod; /// prepare ids FOR(i,n+1) prefs[i] = mp(pref[i], i); sort(prefs,prefs+n+1); FOR(i,n+1) { ids[prefs[i].se] = i; if (i>0 && prefs[i].fi==prefs[i-1].fi) ids[prefs[i].se] = ids[prefs[i-1].se]; } //FOR(i,n+1) cerr << "i = " << i << ", pref = " << pref[i] << ", id = " << ids[i] << "\n"; dp[0] = 1; add(0, 0, 1); FORI(i,n) { /*int tmp_dp = 0; FOR(j,i) { if (pref[j] <= pref[i]) { if (pref[i]%2 == pref[j]%2) tmp_dp += dp[j]; } else { if (pref[i]%2 != pref[j]%2) tmp_dp += dp[j]; } if (dp[i] >= mod) tmp_dp -= mod; }*/ dp[i] = (0LL + get(pref[i]%2, ids[i]) + get(1-pref[i]%2, n) - get(1-pref[i]%2, ids[i]) + mod) % mod; //cerr << "i = " << i << " : dp slow = " << tmp_dp << ", dp fast = " << dp[i] << "\n"; add(pref[i]%2, ids[i], dp[i]); } printf("%d\n", dp[n]); return 0; } |