Skip to content

Latest commit

 

History

History
129 lines (91 loc) · 3.25 KB

problem3.md

File metadata and controls

129 lines (91 loc) · 3.25 KB

$\huge\color{cadetblue}{\text{Problem 3}}$


$\Large{\color{rosybrown}\text{Prob 3.1: }}{\color{darkseagreen}{{\space \mathcal{O}(\sqrt{N})}}}$


int i = 0, j = 0;
while (i < N) {
  j++;
  i += 2*j - 1;
}

The variable $j$ keeps track of the number of iterations. Use is made of Gauss' formula for the sum of the first $j$ integers, but modified such that $i$ is the exact square of $j$: so we have $i = j^2$, and not $i = j(j+1)/2$, at the end of each loop iteration. The loop terminates when $i \geq N$, so we have $j \geq \sqrt{N}$. The fragment's time complexity is therefore in $\mathcal{O}(\sqrt{N})\space$.



$\Large{\color{rosybrown}\text{Prob 3.2: }}{\color{darkseagreen}{{\space \mathcal{O}(\log (N))}}}$


int i = N;
while (i > 1) {
  if (i % 2 == 0) {
    i = i/2;
  } else {
    i++;
  }
}

The variable $i$ is initialized to $N$, and then halved if it is even, or incremented by one to make it even if it is odd. The loop terminates when $i = 1$. In the worst case, $i$ is halved half of the time, and incremented by one the other half of the time. In this case, the loop needs less than $2\log(N)$ iterations to terminate. The fragment's time complexity is therefore in $\mathcal{O}(\log N)$.



$\Large{\color{rosybrown}\text{Prob 3.3: }}{\color{darkseagreen}{{\space \mathcal{O}(N)}}}$


int i = 0, j = N;
while (i < j) {
  i++;
  j--;
}

The variables $i$ and $j$ are incremented and decremented, respectively, until they meet. The loop terminates when $i = j$, after $N/2$ iterations. The fragment's time complexity is therefore in $\mathcal{O}(N)$.



$\Large{\color{rosybrown}\text{Prob 3.4: }}{\color{darkseagreen}{{\space \mathcal{O}(N)}}}$


int i, j, sum = 0, prod = 1;
for (i = 0; i < N; i++) {
  sum++;
}
for (j = 1; j < N; j++) {
  prod = prod * j;
}

The first loop is executed $N$ times, and the second loop is executed $N-1$ times. The loops are independent, so the fragment's time complexity is therefore in $\mathcal{O}(N)$.



$\Large{\color{rosybrown}\text{Prob 3.5: }}{\color{darkseagreen}{{\space \mathcal{O}(N^2)}}}$


int i, j, sum = 0;
for (i = 0; i < N; i++) {
  for (j = 1; j < N; j++) {
    sum++;
  }
}

The inner loop is executed $N-1$ times for each iteration of the outer loop, which is executed $N$ times. The loops are nested, so the fragment's total time complexity is therefore in $\mathcal{O}(N^2)$.



$\Large{\color{rosybrown}\text{Prob 3.6: }}{\color{darkseagreen}{{\space \mathcal{O}(N \log (N))}}}$


int i, j, sum = 0, prod = 1;
for (i = 1; i < N; i++) {
  prod *= i;
}
j = 0;
while (prod > 0) {
  prod = prod / 2;
  j++;
}

The first loop computes the factorial of $N - 1$, in $N - 1$ iterations. The second loop divides $(N-1)!$ by two until it reaches zero, so that this loop's number of iterations is given by:

$$ \begin{align*} & \quad \log \left( (N-1)!\right) \\ < & \quad \log \left( (N)!\right) \\ = & \quad \mathcal{O}(N \log N) \end{align*} $$

The fragment's time complexity is thus determined by the second, most expensive loop, and is therefore in $\mathcal{O}(N \log N)$.