Problem
Test instructions
The starting and ending point of a substring with a length of N of 01 strings in which 1 is the largest proportion of the total length (greater than L).
Analysis
Prefix and S[i] The number of pre-save I have several 1,[j+1,i] this interval 1 of the proportion is (S[i]-s[j])/(I-J), so the problem is converted to find the maximum slope of two points.
, when J is added, it is necessary to remove B1 and B2 to maintain the monotonic increment of slope.
Starting with the points in the queue, the slope of the line at theend of I is the tangent of the lower groove of I and the point in the queue. The points before the tangent point are no longer used because the point after I and their slope will not be as good as the slope of the tangent.
Combination of numbers, slope optimization, monotone queue.
Code
#include <deque> #include <cstdio>using namespace std;deque<int> q;int s[100005];int ansl,ansr;int Great (int a,int b,int c,int D)//ask if the slope of AB is greater than the CD slope {return (s[a]-s[b]) * (c-d)-(S[c]-s[d]) * (A-B);} int main () {int t,l,n,a; scanf ("%d", &t); while (t--) {scanf ("%d%d", &n,&l); Char cc; for (int i=1;i<=n;i++) {Cc=getchar (); s[i]=s[i-1]+cc-' 0 ';//Such reading will not timeout} q.clear (); ansl=0; Ansr=l; for (int i=l; i<=n; i++)//With I do segment right endpoint {int j=i-l; while (Q.size () >1)//J as the left end of the line segment, join the monotone queue {//(monotonically increasing the slope of the monotone) int b1=q[q.size () -1];//the bottom 1th int b2=q[q.size () -2];//2nd if (Great (B1,B2,J,B1) >0)//If b1b2 slope is greater than jb1 q.pop_back (); /Eject B1, maintain monotonic else break;//} q.push_back (j);//j Queue while (Q.size () >1)//GO behind Starting point (left end of line) {//Because the most slope of the and I is the tangent of the lower groove, the point before the pointcut is not optimal if (Great (i,q[0],i,q[1]) <=0)//At the end of the I do q[0]i slope is less than q[1]i slope q.pop_front ();//pop-up team head else break; } int Tmp=great (I,Q[0],ANSR,ANSL),//i and tangent slope, that is, maximum slope if (tmp>0 | | tmp==0 && i-q[0]<ansr- ANSL) {ansl=q[0];//Left endpoint update ansr=i;//right endpoint update}} printf ("%d %d\n ", ANSL+1,ANSR);//The point at the right 1 of the left endpoint is stored, so output +1} return 0;
"UVA 1451" Average