1350. Crossing the Desert description
Princess Zelda has been taken away again. link in order to find her need to cross the Jaolanaro desert, the bad news is that link may not have enough strength to cross the desert, the good news is that the desert is distributed with the fruit of n forces, the bad news is that our link can only go straight. In order to cross the desert, link hopes to eat as much of the fruit of the force as possible. Now ask you to help him plan a straight line so that he can get as much of the fruit of the force as possible.
Input Format
The first line of input has a number n, which indicates the number of fruits in the desert.
The next n rows are two positive integers x, y for each row, representing the coordinates of each force's fruit.
Output Format
Outputs a number that represents the maximum amount of force the forest can gain.
Sample Input
54 42 29 99 1117 8
Sample Output
3
Description
For 70% of data, n<=300
For 100% of data, n<=700
First method: O (N^3)
Take two points, I J as a straight line, and the rest of the points are traversed in this line. Maintain the maximum value,
A few points to note:
1. Start and end of the triple cycle: because I J and J I consist of the same line, it is possible to avoid repetition. and K, too, if there's a point in front of it, so don't think about it.
Or another way of thinking that I is to be judged by the point, J and K are composed of straight lines, so the idea from just now can also reduce the cycle volume.
Or another way of thinking, that each of the points in the same line to make up a subset of the fixed point set, the subset has at least two non-repeating points, the rest of each added to a point can be considered as a third point, so also do not repeat, and about three points collinear formula can be directly applied to the outer product formula.
2. You can use multiplication to avoid division. That's common sense. Good integer arithmetic can solve the problem of making a floating point out how silly it is. Not only slow but also occupy space.
The code is as follows:
/*Judging ... prob=1350 lang=c++accepted (time:6ms, memory:4968kb) Accepted (time:6ms, memory:4964kb) Accepted (time:5ms, memory:495 6KB) Accepted (time:6ms, memory:4952kb) Accepted (time:8ms, memory:4968kb) Accepted (time:11ms, memory:4956kb) Accepted (Time:17ms, MEMORY:4964KB) Accepted (time:140ms, memory:4960kb) Accepted (time:262ms, memory:4968kb) Accepted (time:187ms, memory:4952kb)*/#include<iostream>using namespacestd;intx[701]={0},y[701]={0};//700 points intMainintargcChar Const*argv[]) { intN Cin>>N; for(inti =0; I < n; ++i) {cin>>x[i]>>Y[i]; } //Cn2 enumeration Two points to determine a line//then enumerate each point to determine whether three points are collinear intMax =2; for(inti =0; I < n2; ++i) { for(intj = i+1; J < N-1; ++j) {intCount =2; //I and J make up a straight line if(X[i]==x[j] and y[i]==Y[j])Continue; for(intK = j+1; K < n; ++k) {//study whether the K-point is on the I J Line BOOLIsOn = ((Y[j]-y[i]) * (x[k]-x[i]) = = (X[j]-x[i]) * (y[k]-y[i])); if(isOn) Count++; } if(Count >max) Max=count; }} cout<<max<<Endl; return 0;}
O (n^3)
The second method optimizes a little bit. In fact, the difference between O (N^2LGN) and O (n^3), but the effect is very significant. (Can compare time-consuming)
The idea is to find a point I, work out the slope of the other point and the point, and then find the most repeated occurrences from this set of slopes, the number of points in the same extension direction of I, plus I itself, then you can get "the size of the intersection of a line with I in a given point set". And then find the biggest of these values is the answer.
The essence of this optimization is: In the first method, each time you take three points to judge, actually repeated calculation of certain slopes such as when I j K and I K N Live j K m when the slope of I K and J K is repeated calculation,
And we just have to figure out the slope with the highest rate of slope removal based on the i,j given I arbitrary J to find a pending line.
The specific code is as follows:
/*Judging ... prob=1350 lang=c++accepted (time:7ms, memory:4968kb) Accepted (time:8ms, memory:4956kb) Accepted (time:5ms, memory:494 8KB) Accepted (time:6ms, memory:4960kb) Accepted (time:7ms, memory:4988kb) Accepted (time:9ms, memory:4976kb) Accepted ( Time:12ms, memory:4980kb) Accepted (time:40ms, memory:4984kb) Accepted (time:50ms, memory:4996kb) Accepted (Time:44ms, MEMORY:4988KB)*/#include<iostream>#include<algorithm>#include<cmath>using namespacestd;intx[701]={0},y[701]={0};//700 points structfraction{intSon; intmom; BOOL operator== (Constfraction& b)Const { return(Son*b.mom = = b.son*mom); } BOOL operator!= (ConstFraction &b)Const { return 1-(* This==b); }};fraction scopes[ the];intfreqs[ the]={0}; intCmp_fraction (Const void* _a,Const void*_b) {Fraction* A = (fraction*) _a; Fraction* B = (fraction*) _b; return(*a). Son * (*b). Mom-(*B). Son * (*a). Mom; intMainintargcChar Const*argv[]) { intN Cin>>N; for(inti =0; I < n; ++i) {cin>>x[i]>>Y[i]; } //The slope is determined for each fixed point enumeration successor point intMax =2; intFreqs_len =0; for(inti =0; I < n1; ++i) {//determines the slope set of all lines passing through I points the maximum number of repetitions in this set, which is the maximum of the subset containing I points//each time the Scopes collection is updated, only the length can be recorded. intLen =0; intsame =0; for(intj = i+1; J < N; ++j) {if(X[i]==x[j] and y[i]==Y[j]) {Same++; Continue; } fraction k; K.son= ABS (Y[j]-y[i]);//No, no--K.mom = ABS (x[j]-X[i]); Scopes[len++] =K; } //sort O (NLGN)Qsort (Scopes,len,sizeof(fraction), cmp_fraction); //calculation frequency up to O (n) intMaxFreq =1; intFreq =1; for(intj =1; J < Len; ++j) {if(scopes[j]==scopes[j-1]) Freq++; Else{//it's broken. if(freq>maxFreq) MaxFreq=freq; Freq=1; } } if(freq>maxFreq) MaxFreq=freq; Freqs[freqs_len+ +] = MaxFreq +1+ Same;//Plus I myself } for(inti =0; i < Freqs_len; ++i) {if(Max <Freqs[i]) Max=Freqs[i]; } cout<<max<<Endl; return 0;}
O (N^2LGN)
The structure is used here to represent fractions, instead of floating-point numbers, because floating-point calculation and the process of judging the equal number of floating points is cumbersome (although the code is not the trouble, but the computer should be more difficult to calculate the problem) notice the use of the Qsort function,
There are several other details
1. Storage must be unified with ABS to store, otherwise there will be problems when sorting,
2. Use the same variable to save the same point this should also be considered in the first method.
"Algorithmic Learning Notes" 32. Calculate geometry to find the straight line with the most SJTU OJ 1350 across the desert