Here's the code:
for (int i = 0; i < n; i++) {
for (int j = 0; j < n * n; j++) {
for (int k = 0; k < j; k++) {
sum++;
}
}
}
I need to evaluate the Time complexity in Big-O notation of the nested loops above.
Is it just O(n) * O(n) * O(n) + O(1) to make O(n^3)? Or is there more to it?
The most inner loop is executed in quadratic time (not constant), hence it should be O(n) * O(n^2) * O(n^2) = O(n^5).
Here are all the costs:
Most outer loop - O(n)
The second loop - O(n^2) for each element for the outer loop
The most inner loop - O(n^2) for each element for the second loop
for (int i = 0; i < n; i++) -> runs n times.
for (int j = 0; j < n * n; j++) -> runs n² times.
for (int k = 0; k < j; k++) -> runs n² times (k == j == n²)
n * n² * n² = n^5.
sum+++ is an operation of constant runtime (1) and can therefore be ignored.
The second loop isn't O(n), it's O(n^2) by itself.
Related
I'm having trouble figuring out the time equation for a couple small snippets of code.
int sum = 0;
for (int k = n; k > 0; k /= 2)
for (int i = 0; i < k; i++)
sum++;
int sum = 0;
for (int i = 1; i < n; i *=2)
for (int j = 0; j < i; j++)
sum++;
int sum = 0;
for (int i = 1; i < n; i *=2)
for (int j = 0; j < n; j++)
sum++;
They're all very similar as you can see. I'm not looking for an exact answer or anything, I'm just not really sure where to start with the inner loops. It seems like they would all run n times, but they can't all be the same, right? I'm pretty sure all of the outer loops would be log(n) and that the sum++ would just be a constant (1), but I'm not really sure how all of the inner loops are different and how that would change the equation.
The third code snippet is the easiest to analyze. For each outer loop iteration the inner loop will make 'n' iterations. Since the number of outer loop iterations is O(log(n)) the total number of iterations (and the complexity of the third snippet) is O(n*log(n)).
The first two code snippets have the same complexity, just the outer loop iterates in the descending order in the first snippet, and in the ascending order in the second one. So you iterate over all powers of two which are smaller than 'n', and then repeat the inner loop the corresponding number of times. The total number of iterations is
1 + 2 + 4 + ... + 2^k
where k=log2(n). Sum of powers of 2 is 2^(k+1)=2*2^k=2*n. So, the complexity in both cases is O(n).
int sum = 0;
for (int k = n; k > 0; k /= 2)
for (int i = 0; i < k; i++)
sum++;
n + n/2 + n/4 + n/8 + ... + 1 ≈ 2n = Θ(n)
int sum = 0;
for (int i = 1; i < n; i *=2)
for (int j = 0; j < i; j++)
sum++;
1 + ... + n/8 + n/4 + n/2 + n ≈ 2n = Θ(n)
(Well, not exactly ending with n, n/2 etc, but within a factor of 2 of those, so doesn't matter for the complexity class.)
int sum = 0;
for (int i = 1; i < n; i *=2)
for (int j = 0; j < n; j++)
sum++;
n + n + ... + n ≈ log(n) × n = Θ(n log n)
Q2. Consider the following code fragments (a), (b) and (c) where n is the variable specifying data
size and C is a constant. What is the big-Oh time complexity in terms of n in each case? Show all
necessary steps.
(a)
for (int i = 0; i < n; i = i + C)
for (int j = 0; j < 10; j++)
Sum[i] += j * Sum[i];
(b)
for (int i = 1; i < n; i = i * C)
for (int j = 0; j < i; j++)
Sum[i] += j * Sum[i];
(c)
for (int i = 1; i < n; i = i * 2)
for (int j = 0; j < n; j = j + 2)
Sum[i] += j * Sum[i];
1. for (int i = 0; i < n; i = i + C)
2. for (int j = 0; j < 10; j++)
3. Sum[i] += j * Sum[i];
`
Line 1: int i=0, takes constant time of 1 so O(1)
i<n, takes n+1 time so O(n)
i=i+C, takes n time so O(n)
Total time: 1+(n+1)+n= 2n+2
Line 2:
int j=0, takes constant time of 1 so O(1)
j<10, loops through 10 times and takes n time so O(n)
i=i+C, loops through 10 times and takes n time so O(n)
Total time: 1+(10+10)n= 1+20n
Line 3:
Sum[i]=Sum[i]+j*Sum[i];
Addition and Multiplication takes constant time of 2 and plus 1 to store
or assign the value, and it loops through n times.
Total time:3n
T(n)=(2n+2)+(1+20n)+3n= 25n+3 is O(n) right?
I have a question in regards to the time complexity of the below code. I am guessing that the time complexity is, O(n^3) but my friend told me that the time complexity should be O(n^2). However, I am still not convinced with the answer. My stand is that: the first and second for loop would cost O(1/2 n^2) and inner loop would need another some O(n) complexity. Therefore, it is about O(n^3).
for (int i = 1; i <= len; i++) {
for (int j = i + 1; j <= len; j++) {
int mid = (i + j) / 2;
for (int k = i; k <= j; k++) {
dist[i][j] += Math.abs(A[k - 1] - A[mid - 1]);
}
}
}
So you need to find the time complexity of something like this:
for (int i = 1; i <= N; i++) {
for (int j = i + 1; j <= N; j++) {
for (int k = i; k <= j; k++) {
// some O(1) operation
}
}
}
Each of the loops run in O(N), so the complexity is O(N^3). You can also write a simple test program in your language (I wrote in python):
def check(N):
s = 0
for i in xrange(1, N + 1):
for j in xrange(i + 1, N + 1):
for k in xrange(i, j + 1):
s += 1
return s
print [check(i) for i in xrange(1, 10)] // [0, 2, 7, 16, 30, 50, 77, 112, 156]
And checked for a closed form for this sequence. It is ,
which is clearly O(n^3)
How to find time complexities for the following loops.
1)
int I, j, k, n, mini, tmp;
for(i = 0; i< k; i++){
mini = i;
for(j =i +1; j < n; j++)
if (a[j] < a[mini])
mini = j;
tmp = a[i];
a[i] = a[mini];
a[mini] = tmp;
}
return a[k-1];
}
2)
void SelectionSort(int A[], int n) {
int i = 0;
while (i < n - 1) {
int j = i + 1;
while (j < n) {
if (A[j] < A[i])
swap(A[j], A[i])
j++;
}
i++;
}
}
Both are O(n^2) 1,2
In both, the outer loop runs from 0 to n (exclusive), and for each iteration - the inner loop runs from i+1 to n (exclusive).
If we sum the running time of the inner loops we get:
n- (0+1) + n- (1+1) + .... + n-(n-1 + 1) =
= n-1 + n-2 + .... + 0 =
0 + 1 + ... + n-1 = (*)
n(n-1)/2
which is in O(n^2)
The equation (*) comes from sum of aritmetic progression.
As a side note - both are sorting algorithms, the first is min sort and the second is as the function name says, selection sort.
(1) technically the first is O(k^2), but I assume it means the same here.
(2) Assuming the return a[k-1]; should be AFTER closing the scope of the outer loop, and its placement is a mistake. If it is not a mistake - the outer loop runs only once, and complexity is O(n).
I want to check my understanding of Big-O notation. If I have code:
for(int bound = 1; bound <= n; bound *= 2){
for( int i = 0; i < bound; i++) {
for(int j = 0; j < n; j += 2){
.....Code
}
for(int j = 1; j < n; j *= 2){
......Code
}
}
}
is the Big-O notation for this N3?
Not quite. The outer loop increment is bound *= 2, so that loop is O(log n). The two inner loops (i and the first j loop) are both O(n), so when nested they're O(n2). (You can ignore the j *= 2 inner loop because it's faster than the j += 2 loop and won't significantly contribute to the program's run time.)
Put this all together and the whole program is O(log n * n2).