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
| #include <math.h> #include <stdio.h> void find(int left, int right); void rmq(int n); int a[100005] = {}; int max[100005][20] = {}; int min[100005][20] = {}; int ans = 0; int themin(int x, int y) { if (a[x] < a[y]) return x; return y; } int themax(int x, int y) { if (a[x] >= a[y]) return x; return y; } int minpos(int left, int right) { int k = log(right - left + 1) / log(2); return themin(min[left][k], min[right + 1 - (1 << k)][k]); } int maxpos(int left, int right) { int k = log(right - left + 1) / log(2); return themax(max[left][k], max[right + 1 - (1 << k)][k]); } int main() { int n; scanf("%d", &n); for (int i = 0; i < n; i++) { scanf("%d", &a[i]); max[i][0] = min[i][0] = i; } rmq(n); find(0, n - 1); if (ans == 1) ans = 0; printf("%d", ans); return 0; } void rmq(int n) { int i, j; for (j = 1; (1 << j) <= n; j++) { for (i = 0; i + (1 << j) - 1 < n; i++) { max[i][j] = themax(max[i][j - 1], max[i + (1 << (j - 1))][j - 1]); min[i][j] = themin(min[i][j - 1], min[i + (1 << (j - 1))][j - 1]); } } return; } void find(int left, int right) { if (right <= left) return; int l = minpos(left, right); int r = maxpos(left, right); if (l <= r) { ans = ans > r - l + 1 ? ans : r - l + 1; find(left, l - 1); find(r + 1, right); } else { find(r + 1, l - 1); find(left, r); find(l, right); } return; }
|