I don't want the answer I want to know how to do it.
The efficiency of the algorithm doIt can be expressed as O(f(n))=n^3. Calculate the efficiency of the following program segment exactly and by using the big-O notation.
for (i=1; i<=n+1; i++)
for (j=1; j<n, j++)
doIt (...)
The example he gave us wasn't anything like this he just drew several squares inside of other squares which showed us that it was a nested loop. He didn't give us any type of code like the one in the problem. He just wrote
Alg(m, n, k, l)=3n^3
M=1n, N=1 2n, K=1n, L=1n^2
n^2*n*2n*n*3n^3=6n^8=O(n^8)
So, I'm assuming that this is a nested loop and the highest it goes to is n^3.
Or can someone write the code for the example so I can understand it better?
for (i=1; i<=n+1; i++)
for (j=1; j<n, j++)
doIt (...)
As you mentioned the worst-case complexity is given to be O(n^3).
So, in case of nested loops, the main thing to focus is that the first loop guides the inner loop,i.e., the inner loop will generally run no. of iterations(not necessarily always) than the outer loop!
As in your question, the outer loop runs for i=1 to i=n+1---n+1 times. Similarly, the inner loop runs for j=1 to j < n --- n-1 iterations on each iteration of outer loop .
Also, the function doIt() is inside the inner loop with complexity of order O(n^3).
Next, n+1 iterations are of order O(n) as per worst-case complexity.
Similarly, n-1 iterations are of order of O(n) as per worst-case complexity!
Hence, the overall worst-case complexity = O(n)*O(n)*O(n^3) = O(n^5)...
If you're unable to understand,please leave a comment below!
Related
I think the time complexity of this code will be O(n^2) but I am not sure so if someone can explain what will be the time complexity of this code it would be really helpful
int func2()
{
int i, j, k = 0;
scanf("%d", &n);
for (i = 1; i < n; i++)
{
i -= 1;
i *= 2;
k = k + i;
for (j = 1; j < n; j++);
}
}
It looks like an infinite loop to me, so the time complexity is O(infinity).
On the first iteration of the outer loop, i -= 1 will set i to 0. Multiplying by 2 leaves it still 0.
The loop iteration i++ will then increment i to 1, and the next iteration will repeat the above computations.
I am a beginner on time complexity but these are my views:-
The outer for loop is in the condition of an infinite loop as on the first iteration of the outer loop, execution starts with i=1.
On executing i -= 1 it will set i=0.
Executing i*=2, the value of i remains the same as 0.
On going in the increment phase, i is incremented and i=1.
So the same process occurs.
Thus the value of i remains the same causing it to run indefinitely.
Now, coming forward inside the outer for loop is a nested for (in the variable j) loop that is followed by a semicolon. This causes it to have a time complexity of O(1).
So the resultant overall time complexity can be expected to be O(infinity).
First, 'n' not declared here and input value is being assigned to it.
Second, technically, this code is an infinite loop (done ridiculously hard way) and for non-terminating, forever-running algorithms the time-complexity is 'Undefined' as by the principles of Algorithm Analysis, time-complexity is only computed for algorithms that perform a task with certainity to terminate.
In case if this would have been a terminating loop, time complexity of this function is O(n^2) would have been quadratic in nature due to nesting of for(;;) inside of another for(;;) with enclosed statements of O(1) - linear time complexity. The higher order complexity ( O(n^2) ) supersedes.
I am learning to compute the time complexity of algorithms.
Simple loops and nested loops can be compute but how can I compute if there are assignments inside the loop.
For example :
void f(int n){
int count=0;
for(int i=2;i<=n;i++){
if(i%2==0){
count++;
}
else{
i=(i-1)*i;
}
}
}
i = (i-1)*i affects how many times the loop will run. How can I compute the time complexity of this function?
As i * (i-1) is even all the time ((i * (i-1)) % 2 == 0), if the else part will be true for one time in the loop, i++ makes the i odd number. As result, after the first odd i in the loop, always the condition goes inside the else part.
Therefore, as after the first iteration, i will be equal to 3 which is odd and goes inside the else part, i will be increased by i * (i-1) + 1 in each iteration. Hence, if we denote the time complexity of the loop by T(n), we can write asymptotically: T(n) = T(\sqrt(n)) + 1. So, if n = 2^{2^k}, T(n) = k = log(log(n)).
There is no general rule to calculate the time complexity for such algorithms. You have to use your knowledge of mathematics to get the complexity.
For this particular algorithm, I would approach it like this.
Since initially i=2 and it is even, let's ignore that first iteration.
So I am only considering from i=3. From there I will always be odd.
Your expression i = (i-1)*i along with the i++ in the for loop finally evaluates to i = (i-1)*i+1
If you consider i=3 as 1st iteration and i(j) is the value of i in the jth iteration, then i(1)=3.
Also
i(j) = [i(j-1)]^2 - i(j-1) + 1
The above equation is called a recurrence relation and there are standard mathematical ways to solve it and get the value of i as a function of j. Sometimes it is possible to get and sometimes it might be very difficult or impossible. Frankly, I don't know how to solve this one.
But generally, we don't get situations where you need to go that far. In practical situations, I would just assume that the complexity is logarithmic because the value of i is increasing exponentially.
This is the function:
void f(int n)
{
for(int i=0; i<n; ++i)
for(int j=0; j<i; ++j)
for(int k=i*j; k>0; k/=2)
printf("~");
}
In my opinion, the calculation of the time complexity would end up to be something like this:
log((n-1)(n-2))+log((n-1)(n-3))+...+log(n-1)+log((n-2)(n-3))+...+log(n-2)+...log(2)
So, I get a time complexity of nlog(n!) (because loga+logb=log(a*b) and because n-1,n-2,n-3,... each appears n-1 times in total.
However, the correct answer is n^2*logn, and I have no idea where my mistake is. Could anyone here help?
Thanks a lot!
log(n!) can be approximated as (n+1/2)log(n) - n + constant (see https://math.stackexchange.com/questions/138194/approximating-log-of-factorial)
So the complexity is n*n*log(n) as expected.
Simpler: compute the complexity loop by loop independently and multiply them.
First 2 outer loops: trivial: n each, which makes n^2
Inner loop: has a log(n**2) complexity which is the same as log(n)
So n^2log(n) is the correct answer.
The Complexity is O(N*N*LOG_2(N^2)).
The first and the second loop both have O(N) and the last loop in k has logarithmic grow.
LOG_2(N^2) = 2*LOG_2(N) and
O(N*M)=O(N)*O(M).
O(constant)=1.
So for the grow of the last loop you can write also O(LOG_2(N^2))=O(LOG(N)).
I have the following for loops:
for i = 1 to n
for j = i to n
for k = i to j+1
I think that the complexities for the first and second loop are n and n(n+1)/2 respectively but I’m really stumped as for how to figure out the complexity of the third one. How do I go about finding the complexity for it when both initial and end values are dependent on the previous loops?
First replace each loop with a summation. Do some math...
PS:
These can help:
i=1;
while(i<n*n)
i=i+n;
from my lecturer provided answer:
Big-O notation was O(n) instead O(n^2) why?
Because after each loop run n is added to i. So it has to run maximal n times to reach n², thus ending the loop.
O(n^2) would be:
i=1;
while(i<n*n)
i=i+1;