#include <unordered_map> #include <iostream> constexpr int TWO_20 = 1048576; constexpr int MAX_N = 300000; constexpr long long PRIME = 1000000007; int a[MAX_N]; int n; std::unordered_map<int, int> fCacheMap; long long fIterations = 0; long long gIterations = 0; long long gCache[TWO_20]; int power2(int p) { int result = 1; for (int i = 0; i < p; i++) { result *= 2; } return result; } long long prepareSegmentTree(int nodeIndex, int rangeStart, int rangeEnd) { if (rangeStart == rangeEnd) { gCache[nodeIndex] = a[rangeStart]; return gCache[nodeIndex]; } int rangeMiddle = rangeStart + (rangeEnd - rangeStart) / 2; auto value = prepareSegmentTree(2 * nodeIndex + 1, rangeStart, rangeMiddle) + prepareSegmentTree(2 * nodeIndex + 2, rangeMiddle + 1, rangeEnd); gCache[nodeIndex] = value % PRIME; return gCache[nodeIndex]; } long long getSum(int nodeIndex, int nodeRangeStart, int nodeRangeEnd, int rangeStart, int rangeEnd) { if (rangeStart <= nodeRangeStart && rangeEnd >= nodeRangeEnd) return gCache[nodeIndex]; if (nodeRangeEnd < rangeStart || nodeRangeStart > rangeEnd) return 0; int rangeMiddle = nodeRangeStart + (nodeRangeEnd - nodeRangeStart) / 2; long long result = getSum(2 * nodeIndex + 1, nodeRangeStart, rangeMiddle, rangeStart, rangeEnd) + getSum(2 * nodeIndex + 2, rangeMiddle + 1, nodeRangeEnd, rangeStart, rangeEnd); return result % PRIME; } void readInput() { std::cin >> n; for (int i = 0; i < n; i++) { std::cin >> a[i]; } prepareSegmentTree(0, 0, n - 1); } int g(int start, int end) { long long result = getSum(0, 0, n - 1, start, end); result = result % 2 == 0 ? 1 : 0; return result; } long long f(int end) { if (fCacheMap.find(end) != fCacheMap.end()) { return fCacheMap[end]; } long long result = 0; int i = 0; for (; i < end; i++) { long long firstPart = g(i + 1, end); if (firstPart == 0) continue; long long secondPart = f(i); if (secondPart == 0) continue; result += firstPart * secondPart; result = result % PRIME; } fIterations += i; result += g(0, end); result = result % PRIME; fCacheMap[end] = result; return result; } void solve() { readInput(); auto result = f(n - 1); std::cout << result; } int main() { solve(); 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 96 97 98 99 100 101 | #include <unordered_map> #include <iostream> constexpr int TWO_20 = 1048576; constexpr int MAX_N = 300000; constexpr long long PRIME = 1000000007; int a[MAX_N]; int n; std::unordered_map<int, int> fCacheMap; long long fIterations = 0; long long gIterations = 0; long long gCache[TWO_20]; int power2(int p) { int result = 1; for (int i = 0; i < p; i++) { result *= 2; } return result; } long long prepareSegmentTree(int nodeIndex, int rangeStart, int rangeEnd) { if (rangeStart == rangeEnd) { gCache[nodeIndex] = a[rangeStart]; return gCache[nodeIndex]; } int rangeMiddle = rangeStart + (rangeEnd - rangeStart) / 2; auto value = prepareSegmentTree(2 * nodeIndex + 1, rangeStart, rangeMiddle) + prepareSegmentTree(2 * nodeIndex + 2, rangeMiddle + 1, rangeEnd); gCache[nodeIndex] = value % PRIME; return gCache[nodeIndex]; } long long getSum(int nodeIndex, int nodeRangeStart, int nodeRangeEnd, int rangeStart, int rangeEnd) { if (rangeStart <= nodeRangeStart && rangeEnd >= nodeRangeEnd) return gCache[nodeIndex]; if (nodeRangeEnd < rangeStart || nodeRangeStart > rangeEnd) return 0; int rangeMiddle = nodeRangeStart + (nodeRangeEnd - nodeRangeStart) / 2; long long result = getSum(2 * nodeIndex + 1, nodeRangeStart, rangeMiddle, rangeStart, rangeEnd) + getSum(2 * nodeIndex + 2, rangeMiddle + 1, nodeRangeEnd, rangeStart, rangeEnd); return result % PRIME; } void readInput() { std::cin >> n; for (int i = 0; i < n; i++) { std::cin >> a[i]; } prepareSegmentTree(0, 0, n - 1); } int g(int start, int end) { long long result = getSum(0, 0, n - 1, start, end); result = result % 2 == 0 ? 1 : 0; return result; } long long f(int end) { if (fCacheMap.find(end) != fCacheMap.end()) { return fCacheMap[end]; } long long result = 0; int i = 0; for (; i < end; i++) { long long firstPart = g(i + 1, end); if (firstPart == 0) continue; long long secondPart = f(i); if (secondPart == 0) continue; result += firstPart * secondPart; result = result % PRIME; } fIterations += i; result += g(0, end); result = result % PRIME; fCacheMap[end] = result; return result; } void solve() { readInput(); auto result = f(n - 1); std::cout << result; } int main() { solve(); return 0; } |