The main effect of the topic:
Give a sequence of n numbers, they are 0~n-1, ask whether there are 3 numbers in order in the sequence, which is arithmetic progression.
Ideas:
Use an array to record the position of each number in the sequence, and then enumerate the smallest of the 3 numbers, then enumerate the increment of the arithmetic progression, and finally look at the position of the three digits is not continuous.
n Max is 1W, but the complexity of the algorithm looks like O (n^2), how fast is it? Rough analysis of the complexity of it.
The first layer for loop is 0...N, focusing on the second layer for loop: for (int j=1; I+2*j < n; ++J)
Change the I+2*j < n shifts into:
J < n/(2*i), J is the number of enumerations for the second-level for loop, and we can see that as I grows, J becomes smaller and faster.
When I=1,2,3...N, J to enumerate: N/2, N/4, N/6, N/8, N/10, N/12, ... n/(2*i) times, we can find that when the i=5, the number of J enumeration is less than 10 times times of N, when the number of J at N/10 is n /40, 40 times times less than N. Assuming n equals 1W, then when I=5, J to enumerate 1000 times, when I=20, as long as the enumeration 250 times, the second layer of the spin down is very fast. So the complexity of this algorithm is far less than O (n^2), visual in n log n
Code:
#include <cstdio>
#include <cstring>
#include <cmath>
#include <iostream>
#include <algorithm>
using namespace std;
const int MAXN = 10010;
int n;
int ARR[MAXN];
inline bool Judge (int* a) {for
(int i=0; i<n; ++i) {for
(int j=1; i+2*j<n; ++j) {//enum increment
if (a[i]<a[ I+J]&&A[I+J]<A[I+2*J] |
| A[I]>A[I+J]&&A[I+J]>A[I+2*J]) return
false;
}
return true;
}
int main () {
int x;
while (~SCANF ("%d:", &n) && N) {for
(int i=0; i<n; ++i) {
scanf ("%d", &x);
ARR[X] = i;
}
if (judge (arr)) puts ("yes");
Else puts ("no");
return 0;
}
See more highlights of this column: http://www.bianceng.cnhttp://www.bianceng.cn/Programming/sjjg/