for (; i < limit; i += x) { x += 100; }
Is there an elegant solution to calculate i
and x
without using a loop construct?
My thoughts:
I can use the popular Gauss summation formula 1+2+3+4+...+n = (n*(n+1))/2
and binary search to reduce complexity from O (N) to O (log N) .
Assume i = 0, x = 0 then: i = 0*100 + 1*100 + 2*100 + 3*100 + ... + (n-1)*100 = ((n-1)*n)/2*100 if (i != 0 && x != 0) then: i = i + x+0*100 + x+1*100 + x+2*100 + ... + x+(n-1)*100 = i+x*n + ((n-1)*n)/2*100 Thus (i < limit) = (i+x*n+((n-1)*n)/2*100 < limit)
Now use some kind of binary search to find the largest n
that satisfies the above inequality.
if (i < limit) for (n = 1; i+x*n+((n-1)*n)/2*100 < limit; n -= j, n += 1) for (j = 1; i+x*n+((n-1)*n)/2*100 < limit; n += j, j += j);
Now that I have found the number of iterations n
original loop, i
and x
can be calculated using:
i += x*n+((n-1)*n)/2*100 x += 100*n
Any suggestions? Is there a faster solution to O (1)?
O (1) solution:
const int d = 100; while (i < limit) { i += x; x += d; }
With Daniel, answer how to calculate the number of iterations n
, and then i
and x
in steps O (1). i = i+x*n+((n-1)*n)/2*d
(see above), so we can now solve:
i < limit = i+x*n+(n*(n+1))/2*d < limit = d*n^2 + (2*xd)*n - 2*(limit-i) < 0
The above formula is a quadratic inequality and can be solved using a quadratic formula :
(-b Β± (b^2-4ac)^0.5) / 2a
Thus, the number of iterations n
is equal to:
a = d b = 2*xd c = -2*(limit-i) n = ceil((-b + sqrt(b*b-4*a*c)) / (2*a))
Now that we have found the number of iterations n
initial while (for) loop, we can calculate i
and x
using two formulas (see above):
i += x*n+((n-1)*n)/2*d x += d*n
I tested these formulas with a simple C program and they give the same results as the while (for) loop.