Improve language

This commit is contained in:
Antti H S Laaksonen 2017-05-17 22:42:35 +03:00
parent 9d61b10876
commit 2697233dcb
1 changed files with 33 additions and 35 deletions

View File

@ -299,7 +299,7 @@ For example, in the array
\end{tikzpicture} \end{tikzpicture}
\end{center} \end{center}
the inversions are $(6,3)$, $(6,5)$ and $(9,8)$. the inversions are $(6,3)$, $(6,5)$ and $(9,8)$.
The number of inversions tells us The number of inversions indicates
how much work is needed to sort the array. how much work is needed to sort the array.
An array is completely sorted when An array is completely sorted when
there are no inversions. there are no inversions.
@ -327,22 +327,22 @@ One such algorithm is \key{merge sort}\footnote{According to \cite{knu983},
merge sort was invented by J. von Neumann in 1945.}, merge sort was invented by J. von Neumann in 1945.},
which is based on recursion. which is based on recursion.
Merge sort sorts the subarray \texttt{t}$[a,b]$ as follows: Merge sort sorts a subarray \texttt{t}$[a \ldots b]$ as follows:
\begin{enumerate} \begin{enumerate}
\item If $a=b$, do not do anything, because the subarray is already sorted. \item If $a=b$, do not do anything, because the subarray is already sorted.
\item Calculate the position of the middle element: $k=\lfloor (a+b)/2 \rfloor$. \item Calculate the position of the middle element: $k=\lfloor (a+b)/2 \rfloor$.
\item Recursively sort the subarray \texttt{t}$[a,k]$. \item Recursively sort the subarray \texttt{t}$[a \ldots k]$.
\item Recursively sort the subarray \texttt{t}$[k+1,b]$. \item Recursively sort the subarray \texttt{t}$[k+1 \ldots b]$.
\item \emph{Merge} the sorted subarrays \texttt{t}$[a,k]$ and \texttt{t}$[k+1,b]$ \item \emph{Merge} the sorted subarrays \texttt{t}$[a \ldots k]$ and \texttt{t}$[k+1 \ldots b]$
into a sorted subarray \texttt{t}$[a,b]$. into a sorted subarray \texttt{t}$[a \ldots b]$.
\end{enumerate} \end{enumerate}
Merge sort is an efficient algorithm, because it Merge sort is an efficient algorithm, because it
halves the size of the subarray at each step. halves the size of the subarray at each step.
The recursion consists of $O(\log n)$ levels, The recursion consists of $O(\log n)$ levels,
and processing each level takes $O(n)$ time. and processing each level takes $O(n)$ time.
Merging the subarrays \texttt{t}$[a,k]$ and \texttt{t}$[k+1,b]$ Merging the subarrays \texttt{t}$[a \ldots k]$ and \texttt{t}$[k+1 \ldots b]$
is possible in linear time, because they are already sorted. is possible in linear time, because they are already sorted.
For example, consider sorting the following array: For example, consider sorting the following array:
@ -539,7 +539,7 @@ $O(n)$ time assuming that every element in the array
is an integer between $0 \ldots c$ and $c=O(n)$. is an integer between $0 \ldots c$ and $c=O(n)$.
The algorithm creates a \emph{bookkeeping} array, The algorithm creates a \emph{bookkeeping} array,
whose indices are elements in the original array. whose indices are elements of the original array.
The algorithm iterates through the original array The algorithm iterates through the original array
and calculates how many times each element and calculates how many times each element
appears in the array. appears in the array.
@ -620,7 +620,7 @@ be used as indices in the bookkeeping array.
\index{sort@\texttt{sort}} \index{sort@\texttt{sort}}
It is almost never a good idea to use It is almost never a good idea to use
a self-made sorting algorithm a home-made sorting algorithm
in a contest, because there are good in a contest, because there are good
implementations available in programming languages. implementations available in programming languages.
For example, the C++ standard library contains For example, the C++ standard library contains
@ -749,19 +749,19 @@ struct P {
It is also possible to give an external It is also possible to give an external
\key{comparison function} to the \texttt{sort} function \key{comparison function} to the \texttt{sort} function
as a callback function. as a callback function.
For example, the following comparison function For example, the following comparison function \texttt{comp}
sorts strings primarily by length and secondarily sorts strings primarily by length and secondarily
by alphabetical order: by alphabetical order:
\begin{lstlisting} \begin{lstlisting}
bool cmp(string a, string b) { bool comp(string a, string b) {
if (a.size() != b.size()) return a.size() < b.size(); if (a.size() != b.size()) return a.size() < b.size();
return a < b; return a < b;
} }
\end{lstlisting} \end{lstlisting}
Now a vector of strings can be sorted as follows: Now a vector of strings can be sorted as follows:
\begin{lstlisting} \begin{lstlisting}
sort(v.begin(), v.end(), cmp); sort(v.begin(), v.end(), comp);
\end{lstlisting} \end{lstlisting}
\section{Binary search} \section{Binary search}
@ -770,9 +770,9 @@ sort(v.begin(), v.end(), cmp);
A general method for searching for an element A general method for searching for an element
in an array is to use a \texttt{for} loop in an array is to use a \texttt{for} loop
that iterates through the elements in the array. that iterates through the elements of the array.
For example, the following code searches for For example, the following code searches for
an element $x$ in the array \texttt{t}: an element $x$ in an array \texttt{t}:
\begin{lstlisting} \begin{lstlisting}
for (int i = 0; i < n; i++) { for (int i = 0; i < n; i++) {
@ -783,8 +783,8 @@ for (int i = 0; i < n; i++) {
\end{lstlisting} \end{lstlisting}
The time complexity of this approach is $O(n)$, The time complexity of this approach is $O(n)$,
because in the worst case, it is needed to check because in the worst case, it is necessary to check
all elements in the array. all elements of the array.
If the order of the elements is arbitrary, If the order of the elements is arbitrary,
this is also the best possible approach, because this is also the best possible approach, because
there is no additional information available where there is no additional information available where
@ -801,17 +801,19 @@ in $O(\log n)$ time.
\subsubsection{Method 1} \subsubsection{Method 1}
The traditional way to implement binary search The usual way to implement binary search
resembles looking for a word in a dictionary. resembles looking for a word in a dictionary.
At each step, the search halves the active region in the array, The search maintains an active region in the array,
until the target element is found, or it turns out which initially contains all array elements.
that there is no such element. Then, a number of steps is performed,
each of which halves the size of the region.
First, the search checks the middle element of the array. At each step, the search checks the middle element
of the active region.
If the middle element is the target element, If the middle element is the target element,
the search terminates. the search terminates.
Otherwise, the search recursively continues Otherwise, the search recursively continues
to the left or right half of the array, to the left or right half of the region,
depending on the value of the middle element. depending on the value of the middle element.
The above idea can be implemented as follows: The above idea can be implemented as follows:
@ -827,17 +829,16 @@ while (a <= b) {
} }
\end{lstlisting} \end{lstlisting}
The algorithm maintains a range $a \ldots b$ In this implementation, the active region is $a \ldots b$,
that corresponds to the active region of the array. and initially the region is $0 \ldots n-1$.
Initially, the range is $0 \ldots n-1$, the whole array. The algorithm halves the size of the region at each step,
The algorithm halves the size of the range at each step,
so the time complexity is $O(\log n)$. so the time complexity is $O(\log n)$.
\subsubsection{Method 2} \subsubsection{Method 2}
An alternative method for implementing binary search An alternative method to implement binary search
is based on an efficient way to iterate through is based on an efficient way to iterate through
the elements in the array. the elements of the array.
The idea is to make jumps and slow the speed The idea is to make jumps and slow the speed
when we get closer to the target element. when we get closer to the target element.
@ -860,16 +861,13 @@ if (t[k] == x) {
} }
\end{lstlisting} \end{lstlisting}
The variables $k$ and $b$ contain the position During the search, the variable $b$
in the array and the jump length. contains the current jump length.
If the array contains the element $x$,
the position of $x$ will be in the variable $k$
after the search.
The time complexity of the algorithm is $O(\log n)$, The time complexity of the algorithm is $O(\log n)$,
because the code in the \texttt{while} loop because the code in the \texttt{while} loop
is performed at most twice for each jump length. is performed at most twice for each jump length.
\subsubsection{C++ implementation} \subsubsection{C++ functions}
The C++ standard library contains the following functions The C++ standard library contains the following functions
that are based on binary search and work in logarithmic time: that are based on binary search and work in logarithmic time:
@ -895,7 +893,7 @@ if (k < n && t[k] == x) {
} }
\end{lstlisting} \end{lstlisting}
The following code counts the number of elements Then, the following code counts the number of elements
whose value is $x$: whose value is $x$:
\begin{lstlisting} \begin{lstlisting}