Chapter 15 first version

This commit is contained in:
Antti H S Laaksonen 2017-01-08 15:00:25 +02:00
parent bd6525b526
commit f7090149ec
1 changed files with 41 additions and 44 deletions

View File

@ -560,30 +560,30 @@ The function \texttt{union} ensures that the
length of each path is $O(\log n)$ by connecting length of each path is $O(\log n)$ by connecting
the smaller set to the larger set. the smaller set to the larger set.
\section{Primin algoritmi} \section{Prim's algorithm}
\index{Primin algoritmi@Primin algoritmi} \index{Prim's algorithm}
\key{Primin algoritmi} on vaihtoehtoinen menetelmä \key{Prim's algorithm} is an alternative method
verkon pienimmän virittävän puun muodostamiseen. for finding a minimum spanning tree.
Algoritmi aloittaa puun muodostamisen jostakin The algorithm first adds an arbitrary node
verkon solmusta ja lisää puuhun aina kaaren, to the tree, and then always selects an edge
joka on mahdollisimman kevyt ja joka whose weight is as small as possible and
liittää puuhun uuden solmun. that adds a new node to the tree.
Lopulta kaikki solmut on lisätty puuhun Finally, all nodes have been added to the tree
ja pienin virittävä puu on valmis. and a minimum spanning tree has been found.
Primin algoritmin toiminta on lähellä Prim's algorithm resembles Dijkstra's algorithm.
Dijkstran algoritmia. The difference is that Dijkstra's algorithm always
Erona on, että Dijkstran algoritmissa valitaan selects an edge that creates a shortest path
kaari, jonka kautta syntyy lyhin polku alkusolmusta from the starting node to another node,
uuteen solmuun, mutta Primin algoritmissa but Prim's algorithm simply selects the lightest
valitaan vain kevein kaari, joka johtaa uuteen solmuun. edge that adds a new node to the tree.
\subsubsection{Esimerkki} \subsubsection{Example}
Tarkastellaan Primin algoritmin toimintaa Let's consider how Prim's algorithm works
seuraavassa verkossa: in the following graph:
\begin{center} \begin{center}
\begin{tikzpicture}[scale=0.9] \begin{tikzpicture}[scale=0.9]
@ -605,8 +605,7 @@ seuraavassa verkossa:
%\path[draw=red,thick,-,line width=2pt] (5) -- (6); %\path[draw=red,thick,-,line width=2pt] (5) -- (6);
\end{tikzpicture} \end{tikzpicture}
\end{center} \end{center}
Initially, there are no edges between the nodes:
Aluksi solmujen välillä ei ole mitään kaaria:
\begin{center} \begin{center}
\begin{tikzpicture}[scale=0.9] \begin{tikzpicture}[scale=0.9]
\node[draw, circle] (1) at (1.5,2) {$1$}; \node[draw, circle] (1) at (1.5,2) {$1$};
@ -625,10 +624,9 @@ Aluksi solmujen välillä ei ole mitään kaaria:
%\path[draw,thick,-] (3) -- node[font=\small,label=left:3] {} (6); %\path[draw,thick,-] (3) -- node[font=\small,label=left:3] {} (6);
\end{tikzpicture} \end{tikzpicture}
\end{center} \end{center}
We can select an arbitrary node as a starting node,
Puun muodostuksen voi aloittaa mistä tahansa solmusta, so let's select node 1.
ja aloitetaan se nyt solmusta 1. First, an edge with weight 3 connects nodes 1 and 2:
Kevein kaari on painoltaan 3 ja se johtaa solmuun 2:
\begin{center} \begin{center}
\begin{tikzpicture}[scale=0.9] \begin{tikzpicture}[scale=0.9]
\node[draw, circle] (1) at (1.5,2) {$1$}; \node[draw, circle] (1) at (1.5,2) {$1$};
@ -648,10 +646,9 @@ Kevein kaari on painoltaan 3 ja se johtaa solmuun 2:
\end{tikzpicture} \end{tikzpicture}
\end{center} \end{center}
Nyt kevein uuteen solmuun johtavan After this, there are two edges with weight 5,
kaaren paino on 5, so we can add either node 3 or node 5 to the tree.
ja voimme laajentaa joko solmuun 3 tai 5. Let's add node 3 first:
Valitaan solmu 3:
\begin{center} \begin{center}
\begin{tikzpicture}[scale=0.9] \begin{tikzpicture}[scale=0.9]
\node[draw, circle] (1) at (1.5,2) {$1$}; \node[draw, circle] (1) at (1.5,2) {$1$};
@ -672,7 +669,7 @@ Valitaan solmu 3:
\end{center} \end{center}
\begin{samepage} \begin{samepage}
Sama jatkuu, kunnes kaikki solmut ovat mukana puussa: The process continues until all nodes have been included in the tree:
\begin{center} \begin{center}
\begin{tikzpicture}[scale=0.9] \begin{tikzpicture}[scale=0.9]
\node[draw, circle] (1) at (1.5,2) {$1$}; \node[draw, circle] (1) at (1.5,2) {$1$};
@ -693,19 +690,19 @@ Sama jatkuu, kunnes kaikki solmut ovat mukana puussa:
\end{center} \end{center}
\end{samepage} \end{samepage}
\subsubsection{Toteutus} \subsubsection{Implementation}
Dijkstran algoritmin tavoin Primin algoritmin voi toteuttaa
tehokkaasti käyttämällä prioriteettijonoa.
Primin algoritmin tapauksessa jono sisältää kaikki solmut,
jotka voi yhdistää nykyiseen komponentiin kaarella,
järjestyksessä kaaren painon mukaan kevyimmästä raskaimpaan.
Primin algoritmin aikavaativuus on $O(n + m \log m)$
eli sama kuin Dijkstran algoritmissa.
Käytännössä Primin algoritmi on suunnilleen
yhtä nopea kuin Kruskalin algoritmi,
ja onkin makuasia, kumpaa algoritmia käyttää.
Useimmat kisakoodarit käyttävät kuitenkin Kruskalin algoritmia.
Like Dijkstra's algorithm, Prim's algorithm can be
efficiently implemented using a priority queue.
In this case, the priority queue contains all nodes
that can be connected to the current component using
a single edge, in increasing order of the weights
of the corresponding edges.
The time complexity of Prim's algorithm is
$O(n + m \log m)$ that equals the time complexity
of Dijkstra's algorithm.
In practice, Prim's algorithm and Kruskal's algorithm
are both efficient, and the choice of the algorithm
is a matter of taste.
Still, most competitive programmers use Kruskal's algorithm.