\documentclass[10pt,a4paper]{article}
\usepackage[latin1]{inputenc}
\usepackage{amsmath}
\usepackage{amsfonts}
\usepackage{amssymb}
\usepackage{graphicx}
\usepackage{float}
\usepackage{listings}
\author{Michele De Vita}
\title{Exercises week 5}
\begin{document}
	\maketitle
	\begin{enumerate}
		\item
		\begin{align*}
	 &i) \,\,\, \mathbf{C} = (0,  5, -7, 0), &d = -2  \\
		& ii) \,\,\, \mathbf{C} = \left( \begin{matrix}
		0 & 1 & -1 & 0 & 0 \\
		0 & 0 & 1 & -1 & 0
		\end{matrix} \right) ,  &d= \left( \begin{matrix}
		0 \\
		0
		\end{matrix} \right)
		\end{align*}
		\item
		This plot shows the SSE in function of $ \beta $:
		\begin{figure}[H]
			\centering
			\includegraphics[width=0.7\linewidth]{plot_ftest}
		\end{figure}
		The F-test score is $ \dfrac{SSE_{H_0} - SSE}{SSE} $ where $ SSE = SSE(\hat{\beta}) $ that is the y in the plot where $ x = \hat{\beta} $ and $ SSE_{H_0} = SSE(\beta = 1) $\\
		The plot for the numerator of Wald test is the same of the previous because the numerator is the same except for a square difference instead of normal difference.\\
		The main difference between F-test and Wald test is the denominator in the first is $ \hat{\theta} $ while in the second is $ var(\hat{\theta}) $. There is also a relation between test statistics $ F $ and $ W $: $ W = rF $
		\item The confidence interval for $ \mu_0  $ is $ \mathbf{x}_0' \hat{\beta} \pm t_{n-p}(1-\alpha / 2) \hat{\sigma} (\mathbf{x}_0' (\mathbf{X'X})^{-1} x_0)^{1/2}$ while for prediction is $ \mathbf{x}_0' \hat{\beta} \pm t_{n-p}(1-\alpha / 2) \hat{\sigma} (1 + \mathbf{x}_0' (\mathbf{X'X})^{-1} x_0)^{1/2}$. The difference between the two formulas is the "$ 1\,\,+ $" near $ x_0 $ that become from the fact that the estimation try to give an confidence interval of a parameter , so with no variance, while the prediction try to estimate a aleatory variable with a expected value and a variance.
		\item $ f(x_0) = \mathbf{x}_0' \hat{\beta} \pm t_{n-2}(1-\alpha / 2) \hat{\sigma} (1 + \mathbf{x}_0' (\mathbf{X'X})^{-1} x_0)^{1/2}$
		where $ X = $
		$ \left( \begin{matrix}
			1 & x_{11} \\
			\vdots & \vdots  \\
		1 & x_{n1}
			\end{matrix} \right)$ and $ p = 2 $.\\
			The length of interval is minimum when $ \mathbf{x_0 = \mu}  $ because we can write the product $ \mathbf{x_0'(X'X)^{-1}x_0}  $ as $ \dfrac{\sum(x_i - x_0)^2}{dev(x)} $ then the numerator $  \sum(x_i - x_0)^2 $ is minimized when $ x_0 = \mu $
			\item Increasing the number of parameters is not always a good idea: we can express the SPSE (expected squared prediction error as):
			$ \underbrace{n\sigma^2}_{irreducible\,\,  part} + \underbrace{|M|\sigma^2}_{Variance \,\, error} + \underbrace{\sum_{i=1}^{n} (u_{i M} - u_i)^2}_{BIAS^2} $
			\item If we consider only $ \mathbf{X_1} $ we have $ \mathbf{X = X_1} $ then
			\begin{align*}
				E\left[ \tilde{\beta}_1 \right]		&= E \left[ \mathbf{(X_1'X_1)^{-1} X_1'y} \right] \\
				&=  \mathbf{(X_1'X_1)^{-1} X_1' } E \left[ \mathbf{y} \right] \\
				&=  \mathbf{(X_1'X_1)^{-1} X_1' (X_1 \beta_1 + X_2 \beta_2)} \\
				&= \beta_1 +\mathbf{(X_1'X_1)^{-1} X_1'  X_2 \beta_2}
			\end{align*}
			The bias vanish if $ \mathbf{X_1'  X_2  = 0} $ that in statical words mean that $ \mathbf{X_1} \text{ and } \mathbf{X_2} $ are uncorrelated or when $ \mathbf{\beta_2}  $ is irrelevant
			\item If we omit a relevant covariate, we can have a decrease the variance of model such that the increase of $ bias^2 $ is overall convenient
			\item $ SPSE = \sum (y_{n+i} - \hat{y}_{iM}^2) $. See point 5
			\item
			\begin{align*}
			E\left( SSE \right) &= E\left( \sum \left( y_i - \hat{y}_{iM} \right)^2 \right)  \\
			&= E \left( \mathbf{\varepsilon' \varepsilon} \right) \\
			&= (n-p) \sigma^2 \\
			&= E(SPSE) - 2  |M|\sigma^2 \\
			&= n \sigma^2 + |M|\sigma^2 -2 |M|\sigma^2 \\
			&= n \sigma^2 - |M|\sigma^2 \\
			&= (n-p)\sigma^2
			\end{align*}
			$ SSE $  underestimate the $ SPSE $ because $ \hat{SPSE} = \hat{SSE} + 2  |M| \hat{\sigma}^2$ .\\
			This bias is more severe for complex models because the bias is proportional to model complexity
			\item $ AIC =n \log(\hat{\sigma}^2) + 2 (|M| + 1) $\\
			$ BIC = n \log(\hat{\sigma}^2) + \log(n) (|M| + 1) $.\\
			Since $ SPSE  $ is not observable the two latter indicators are used to evaluate the fit of the model.\\
			The difference between $ AIC \text{ and } BIC $ is the term before $ (|M| + 1) $: in AIC is equal to 2 while in BIC is $ \log(n) $. This mean that BIC have a major penalty when the model complexity increase in big dataset.\\
			Next we can see the tables with the results:
			\begin{center}
			\begin{tabular}{|c|c|c|}
				\hline
				n = 100 & AIC & BIC \\
				\hline
				$ l = -300, |M| = 5 $ & 612 & 627.63 \\
				\hline
				$ l = -290, |M| = 9 $ & 600 & 626.05 \\
				\hline
			\end{tabular} \\ \medskip
			\begin{tabular}{|c|c|c|}
				\hline
				n = 200 & AIC & BIC \\
				\hline
				$ l = -300, |M| = 5 $ & 612 & 631.79 \\
				\hline
				$ l = -290, |M| = 9 $ & 600 & 632.98 \\
				\hline
			\end{tabular} \\
		\end{center}
			Between $ n = 100 $ and $ n = 200 $ we can note the phenomenon described before with BIC, because with $ n = 100 $ there is a decrement of BIC between the two configurations while for $ n = 200 $ the BIC increase between the two configurations

			\item $ VIF_j = \dfrac{1}{1 - R_j^2} $.\\It measures the correlation between the covariate $ x_j $ with the other covariates. The greater is $ R^2_j \in [0,1]$ the greater is $ VIF_j $. An empiric alert for variance is when $ VIF_j > 10 $
			\item The ridge regression add a penalty term $ \lambda $ to the linear regression. The $ \mathbf{PLS(\beta) = (y - X \beta)'(y - X \beta) + \lambda \beta' \beta} $.\\The ridge regression is biased respect to linear regression:\\
			$ E_{LS}(\hat{\beta}) = \mathbf{(X'X)^{-1} X'X \beta = \beta} $\\
			$   E_{PLS}(\hat{\beta}) = \mathbf{(X'X + \lambda X'X)^{-1} X'X \beta} $   (when penalty = 0 $  E_{PLS}(\hat{\beta}) = E_{LS}(\hat{\beta})   $)\\
			When $ \lambda $ increases the coefficients $\beta $ tends to zero because $ \mathbf{\lambda K = (X'X + \lambda K)- X'X} $. If we multiply two definite semipositive matrices $ \mathbf{(X'X + \lambda K)^{-1}} $ with $  \mathbf{(X'X + \lambda K)- X'X}  $ also the result is definite semipositive  that is $ \mathbf{I_p - (X'X + \lambda K)^{-1}X'X}  $. This imply that $ \mathbf{(X'X + \lambda K)^{-1}X'X}    $ have the diagonal elements between $[0,1] $ and this term appears when we express $ \hat{\beta}_{PLS} $ in function of $ \hat{\beta}_{LS} $:\\
			$ \hat{\beta}_{PLS} =  \mathbf{(X'X + \lambda K)^{-1}X'X \beta_{LS}}   $\\
			The covariance matrix of $ \hat{\beta}_{PLS} $ for the same reason is lower than variance of $ \hat{\beta}_{LS} $ so in some cases can be convenient use a ridge regression when the bias error is less relevant than variance error
	\end{enumerate}
	\subsection*{Stata code}
	\lstinputlisting{stata_ex.do}
\end{document}


%!TEX TS-program = lualatex
%!TEX encoding = UTF-8 Unicode

\documentclass[12pt]{exam}

%\printanswers

\usepackage{fontspec}
\setmainfont[Ligatures={TeX}, BoldFont={* Bold}, ItalicFont={* Italic}, BoldItalicFont={* BoldItalic}, Numbers={Monospaced, Lining}]{Linux Libertine O}
\setsansfont[Scale=MatchLowercase,Ligatures=TeX]{Linux Biolinum O}
\setmonofont[Scale=MatchLowercase]{Inconsolatazi4}
\newfontfamily{\tablenumbers}[Numbers={Monospaced,Lining}]{Linux Libertine O}
\usepackage{microtype}

\usepackage{amsmath}

\usepackage{unicode-math}
\setmathfont[Scale=MatchLowercase]{TeX Gyre Termes Math}

\usepackage{geometry}
\geometry{letterpaper, left=1.5in, bottom=1in}
%\geometry{landscape}                % Activate for for rotated page geometry
\usepackage[parfill]{parskip}    % Activate to begin paragraphs with an empty line rather than an indent

\usepackage{longtable}

%\usepackage{siunitx}
\usepackage{booktabs}
\usepackage{array}
\newcolumntype{L}[1]{>{\raggedright\let\newline\\\arraybackslash\hspace{0pt}}m{#1}}
\newcolumntype{C}[1]{>{\centering\let\newline\\\arraybackslash\hspace{0pt}}m{#1}}
\newcolumntype{R}[1]{>{\raggedleft\let\newline\\\arraybackslash\hspace{0pt}}m{#1}}

\usepackage{enumitem}
\setlist{leftmargin=*}
\setlist[1]{labelindent=\parindent}
\setlist[enumerate]{label=\textsc{\alph*}.}
\setlist[itemize]{label=\color{gray}\textbullet}
%\usepackage{hyperref}
%\usepackage{placeins} %PRovides \FloatBarrier to flush all floats before a certain point.
%\usepackage{hanging}

\usepackage[sc]{titlesec}

%% Commands for Exam class
\renewcommand{\solutiontitle}{\noindent}
\unframedsolutions
\SolutionEmphasis{\bfseries}

\pagestyle{headandfoot}
\firstpageheader{\textsc{bi}\,163 Evolution and Ecology}{}{\ifprintanswers\textbf{KEY}\else Name: \enspace \makebox[2.5in]{\hrulefill}\fi}
\runningheader{}{}{\footnotesize{pg. \thepage}}
\footer{}{}{}
\runningheadrule

\begin{document}

\subsection*{Shannon-Wiener diversity practice problems}

%The species diversity of a community can be estimated by random sampling of individuals from the community. You can calculate \textit{species richness}, which is the total number of unique species in your sample. You can also calculate \textit{relative abundance}, which the proportion of individuals for each species out of the total number of individuals in your sample.
%
%Species richness and relative abundance (also known as evenness) can be combined mathematically to represent the \textit{species diversity} of a community with a single value (the diversity index). The number by itself does not tell you too much but communities with higher indices have higher diversity.

Species diversity for a sample can be calculated with any of several different equations. The equation we will use is called the Shannon-Wiener diversity index, or Shannon index for short. The Shannon equation is

\[H^{\prime} = -\sum p_i \ln p_i,\]

where $H^{\prime}$ is the index, $p_i$ is the relative abundance of each species, $ln$ is the natural logarithm, and $\sum$ indicating summing across all species. Notice the negative sign before the summation symbol. This will make the final index positive, as you will see below.

Here is an example calculation with the number of individuals from each of 5 species.

\begin{tabular}{llllll}
Species & A & B & C & D & E \tabularnewline
Number & 11 & 23 & 17 & 24 & 28 \tabularnewline
\end{tabular}

The calculations are summarized in the table at the end of the list.

\begin{enumerate}
\item Calculate the total number of individuals in the sample, $11 + 23 + 17 + 24 + 28 = 103.$

\item Calculate $p_i$ by dividing the number of individuals for each species by the total number of individuals, e.g., 11/103 = 0.107, etc.
%
%\begin{tabular}{lrr}
%Species & $n$ & $p_i$ \tabularnewline
%\toprule
%A & $11$ & $0.107$ \tabularnewline
%B & $23$ & $0.223$ \tabularnewline
%C & $17$ & $0.165$ \tabularnewline
%D & $24$ & $0.233$ \tabularnewline
%E & $28$ & $0.272$ \tabularnewline
%\bottomrule
%\end{tabular}

\item Calculate the natural log of each $p_i$. This is the “ln” key on your calculator. If your calculator does not have a natural log key, use the “log” key for $\log_{10}$. You will get a different result but that is OK. You are comparing numbers (larger = more diverse) so the actual values do not matter much. If your calculator does not have either key, get a better calculator!

%\begin{tabular}{lrrr}
%Species & $n$ & $p_i$ & $\ln p_i$\tabularnewline
%\toprule
%A & $11$ & $0.107$ & $-2.235$ \tabularnewline
%B & $23$ & $0.223$ & $-1.501$ \tabularnewline
%C & $17$ & $0.165$ & $-1.802$ \tabularnewline
%D & $24$ & $0.233$ & $-1.457$ \tabularnewline
%E & $28$ & $0.272$ & $-1.302$ \tabularnewline
%\bottomrule
%\end{tabular}
%
\item Multiply the two values together, e.g., $0.107 \times -2.235 = -0.239$ and so on.

%\begin{tabular}{lrrrr}
%Species & $n$ & $p_i$ & $\ln p_i$ & $p_i \ln p_i$ \tabularnewline
%\toprule
%A & $11$ & $0.107$ & $-2.235$ & $-0.239$ \tabularnewline
%B & $23$ & $0.223$ & $-1.501$ & $-0.335$ \tabularnewline
%C & $17$ & $0.165$ & $-1.802$ & $-0.297$ \tabularnewline
%D & $24$ & $0.233$ & $-1.457$ & $-0.339$ \tabularnewline
%E & $28$ & $0.272$ & $-1.302$ & $-0.354$ \tabularnewline
%\bottomrule
%\end{tabular}

\item Sum together the values in the final column.

\item Notice the final sum is a negative value. That is why the negative sign appears before the summation symbol in the equation above. It turns the final value positive.
\end{enumerate}

\begin{tabular}{lrrrr}
Species & $n$ & $p_i$ & $\ln p_i$ & $p_i \ln p_i$ \tabularnewline
\toprule
A & $11$ & $0.107$ & $-2.235$ & $-0.239$ \tabularnewline
B & $23$ & $0.223$ & $-1.501$ & $-0.335$ \tabularnewline
C & $17$ & $0.165$ & $-1.802$ & $-0.297$ \tabularnewline
D & $24$ & $0.233$ & $-1.457$ & $-0.339$ \tabularnewline
E & $28$ & $0.272$ & $-1.302$ & $-0.354$ \tabularnewline
\midrule
  &  $103$    &         & \hfill $\sum$ & $-1.564$\tabularnewline
\bottomrule
\end{tabular}

The Shannon diversity for this sample is $H^{\prime} = 1.564.$

\subsection*{Practice Problems}

Calculate $H^{\prime}$ for each community, then identify the most and least diversity communities.  The correct answers for $\ln$ and $\log_{10}$ are given for you to check your work. Be sure to compare values calculated by the same logarithm function (i.e., only $\ln$ or only $\log_{10}$). Your numbers may be off slightly due to rounding but you should not be off by more than 0.010 or so.

\begin{enumerate}[label=\textsc{Community \alph*:}]

\item 74 71 75 84 55 56 71 54

 Answer $\ln: 2.067$

 Answer $\log_{10}: 0.898$

\item 90 93 65 85 74 91 73 85

 Answer $\ln: 2.072$

 Answer $\log_{10}: 0.900$

\item 65 65 90 51 83 99 50 52

 Answer $\ln: 2.047$

 Answer $\log_{10}: 0.889$

\item 80 43 37 77 94 10 67 63

 Answer $\ln: 1.965$

 Answer $\log_{10}: 0.854$

\item 80 82 66 50 38 87 31 38

 Answer $\ln: 2.014$

 Answer $\log_{10}: 0.875$

\end{enumerate}

Community B is the most diverse. Community D is the least diverse.

\end{document}


%%%%%%%%%%%%%%%%%%%%%%%%
%
%   Thesis template by Youssif Al-Nashif
%
%   May 2020
%
%%%%%%%%%%%%%%%%%%%%%%%%

\section{Introduction}

\subsection{ Skip-grams}
\hspace*{0.3cm} As an alternative to natural language processing (NLP) methods, which are reliant on ``bag-of-words" methods, the methods used here utilize a graph representation of the text. Consider a bigram, a pair of two words\textemdash like ``hot dog" or ``peanut butter", these bigrams can be constructed for a text document where every pair or adjacent words is a bigram. The bigrams can then be used to make a graph, where each word is a vertex, and each bigram is an edge. This graph representation holds more context than the bag-of-words methods; for example seeing the words ``cake" and ``carrot" in a bag of words may not show that ``carrot cake" was the real intent of the text. This is an important concept for modeling text, as we should strive to achieve a representation of the text that makes for effective modeling that will capture the true meaning of the text in question. Keeping this in mind, with the example of ``carrot cake", what about the idiom ``beating a dead horse"? Each word individually may mean something other than the idiom. Even the bigrams ``beating dead" and ``dead horse" do not capture what the idiom means. We can expand the number of words in the n-gram to be 3 or 4 words, or alternatively, we can make more ``edges" or connect more words. We can connect words that are not immediately adjacent but perhaps within $k$ words away. These bigrams that appear within $k$ words of each other are called ``skip-grams". The skip-gram allows to capture context of larger sequences of words since the graph representation will show how the $k$ wide neighborhood of words was connected. In the idiom example, using skip-grams with window width $k = 2$, and removing common words (e.g. ``a", ``at", ``the"), will produce a graph like:

$$
E(G) = \{
\text{beat}  \longleftrightarrow \text{dead},
\text{dead}  \longleftrightarrow \text{horse},
\text{horse}  \longleftrightarrow \text{beat} \}
$$

This graph representation contains a cycle, of length 3, where most native english speakers will identify the meaning behind the graph representation. As ideas, idioms, figures of speech, and other concepts (that may be explained in a non-literal fashion) grow in size as they include more words, it becomes more difficult to capture the meaning behind the text. However, leveraging the concept of a skip gram can produce such a rich graph representation of the text that the original meaning is more likely to be preserved. Other research has shown that use of skip-grams for text modeling leads to less data sparsity and mitigates issues of variety in large corpuses through modeling text in this way. The skip-grams are shown to preserve more context than traditional bag-of-words methods that use words as the token of choice \cite{guthrie2006closer}.\\

\subsection{ Graph Kernels}
\hspace*{0.3cm} The next natural question is, ``how can we compare these graph representations?", and we address this with graph kernel methods. These methods are generally used to compare the similarity of graphs. These use of a graph kernel to compare graphs was first published in 2003, and since then various applications and adaptations have been made to the methods. In the case of text mining, the graph kernel must assess vertex labels \textemdash if one intends to map words to vertices, otherwise they will be assessing the topology alone. In this study, the Edge-Histogram kernel is the kernel used to compute similarity. This kernel was chosen as it uses labels on the graph structure, and is not as computationally intensive as other methods \cite{sugiyama2015halting}. In the specific implementation used for these studies, the computation time was the shortest when compared with other kernel methods like: graphlet, random walk, and Weisfeiler-Lehman kernel \cite{sugiyama2015halting}. Since the data sets of concern in the studies feature either large graphs or a large number of graphs, the kernel had to be cheap computationally.\\

To compute and edge histogram kernel on two graphs, $G_1$ and $G_2$, first define the set of edges $E_i =\{ (u_1,v_1), (u_2,v_2), ... , (u_n,v_n) \}$ where $(u_n,v_n)$ is the $n$-th edge connecting $u_n$ to $v_n$. Then the edge label histogram is defined to be $\vec{g} = \{ g_1, g_2, ... , g_s\}$, so that $g$ contains the number of times each edge label appeared. In the case of graphical representations of text, the number of times a skip-gram appears is not considered; it either appeared or did not. For this reason, a Manhattan distance is chosen, as opposed to a euclidean or similar distance metric, since the Manhattan distance measures distance along a grid\textemdash like Manhattan city blocks from point A to point B. Since the data are all on a grid in essence, due to the binary nature of either having a label or not, the Manhattan distance is a natural fit here. The kernel is then the sum or the product of each element in the $g$ vectors for each $G_1$ and $G_2$ in the case of a linear kernel \cite{sugiyama2015halting}.

%https://papers.nips.cc/paper/2015/file/31b3b31a1c2f8a370206f111127c0dbd-Paper.pdf

\subsection{Using Kernel for Clustering}

\hspace*{0.3cm} The output of the kernel is useful for a variety of tasks. Some other popular applications have included classification with support vector machines, which are popular with other kernel methods. In this case, the kernel is used for unsupervised clustering. Within the kernel matrix, $K$, the entry $k_{i,j}$ represents the similarity between graphs $i$ and $j$. This matrix which contains measures of similarity between points can be used as a distance matrix for hierarchical clustering. Before using the graph kernel as a distance matrix, normalization or standardization takes place, and principal component analysis may be used. The end result is each row is a single graph-document being described by its similarity to all the other graphs, which are the column values. Once the values are transformed or rotated by preprocessing methods, the points are just represented by their similarity to one another, but in a transformed space. Various hyper parameters can be tuned for successful clustering; the graph kernel has a parameter that can be tuned, and the hierarchical clustering can be tried with differing types of linkage.

%\subsection{Kernel Density Estimation Clustering for Linear Kernel}

%In addition to hierarchical clustering, a method was developed to find potential clusters based on the kernel similarity measure, but while measuring similarity to a single graph. For example, we can compare how similar graphs $B$ and $C$ without computing their similarity, by comparing how similar they are to graph $A$; this extension of transitive property logic allows for focusing on the similarity of the graph list as it relates to just one graph.


\hypertarget{haskell-types}{%
\section{Haskell Types}\label{haskell-types}}

\hypertarget{types-of-lists-and-tuples}{%
\subsection{Types of Lists and Tuples}\label{types-of-lists-and-tuples}}

After declare x = `x':

\begin{lstlisting}[language=Haskell]
x ==> Char
'x' ==> Char
"x" ==> [Char]
['x'] ==> [Char]
[x, 'x'] ==> [Char]
[x, x, x, x] ==> [Char]
['x', "x"] ==> error
[x, True] ==> error
[x == 'x', True] ==> [Bool]
[["True"]] ==> [[[Char]]]
[[ True, False], True] ==> error
[[ True, False], []] ==> [[Bool]]
('x') ==> Char
(x , 'x') ==> (Char, Char)
(x ,x, x, x) ==> (Char, Char, Char, Char)
('x', "x") ==> (Char, [Char])
(x , True) ==> (Char, Bool)
(x == 'x' ,True) ==> (Bool, Bool)
(("True")) ==> [Char]
((True ,False) ,True) ==> ((Bool, Bool), Bool)
((True, False), ()) ==> ((Bool, Bool), ())
\end{lstlisting}

\hypertarget{types-of-lists}{%
\subsection{Types of Lists}\label{types-of-lists}}

\begin{lstlisting}[language=Haskell]
After declare a = [True]:

a ==> [Bool]
a ++ a ++ [True] ==> [Bool]
a ++ [] ==> [Bool]
head a ==> Bool
tail a (*) ==> error
head 'x' ==> error
head "x" ==> Char
tail "x" (*) ==> error
"dimdi" !! 2 ==> Char (Gibt den dritten Buchstaben aus (0 indexiert))
"dimdi" ++ "ding" ==> [Char]
\end{lstlisting}

\hypertarget{types-of-functions-and-lists}{%
\subsection{Types of Functions and
Lists}\label{types-of-functions-and-lists}}

\begin{lstlisting}[language=Haskell]
f1 :: Int -> Int
f1 x = x^2 + x + 1
f2 :: Int -> Int
f2 x = 2 * x + 1

f1 ==> Int -> Int
f1 5 ==> Int
f1 f2 ==> error
f1 (f2 5) ==> Int
[f1 5, f2 6, 5, 6] ==> [Int]
[f1, f2, f1] ==> [Int -> Int]
[f1 5, f2] ==> error
(f1 5, f2) ==> (Int, Int -> Int)
([f1, f2, f1] !! 1) 3 ==> Int
([f1, f2, f1] !! 5) 3 (*) ==> error
\end{lstlisting}

\hypertarget{types-of-functions-with-currying}{%
\subsection{Types of Functions with
Currying}\label{types-of-functions-with-currying}}

\begin{lstlisting}[language=Haskell]
g1 :: Int -> Int -> Int -> Int
g1 x y z = x^2 + y^2 + z^2
g2 :: Int -> Int -> Int
g2 x y = 2*x + 2*y

g1  ==> Int -> Int -> Int -> Int
g1 2 ==> Int -> Int -> Int
g1 2 3 ==> Int -> Int
g1 2 3 4 ==> Int
g1 2 3 4 5 ==> eroor
(g1, g2) ==> (Int -> Int -> Int -> Int, Int -> Int -> Int)
(g1 2, g2) ==> (Int -> Int -> Int, Int -> Int -> Int)
(g1 2 3, g2 4) ==> (Int -> Int, Int -> Int)
(g1 2 3 4, g2 4 5) ==> (Int, Int)
[g1, g2] ==> error
[g1 2, g2] ==> [Int -> Int -> Int]
[g1 2 3, g2 4] ==> [Int -> Int]
[g1 2 3 4, g2 4 5] ==> [Int]
\end{lstlisting}

\clearpage


\section{Safety}
\label{membership:safety}

Preserving safety is the first challenge for configuration changes.
For the mechanism to be safe,
there must be no point during the transition where it is possible for
two leaders to be elected for the same term. If a single configuration
change adds or removes many servers, switching the cluster directly from
the old configuration to the new configuration can be unsafe;
it isn't possible to atomically switch all of the servers at once, so
the cluster can potentially split into two independent majorities
during the transition (see
Figure~\ref{fig:membership:reconfigurationdifficulty}).

\begin{figure}
\centering
\includegraphics[scale=.50]{membership/reconfigurationdifficulty}
\vcaption[safety challenge]{
Switching directly from one configuration to another can be
unsafe because different servers will switch at different times.
In this example, the cluster grows from three servers to five.
Unfortunately, there is a point in time where two different leaders
can be elected for the same term,
one with a majority of the old
configuration (\cold{}) and another with a majority of the new
configuration (\cnew{}).
}
\label{fig:membership:reconfigurationdifficulty}
\end{figure}

\begin{figure}
\centering

\begin{subfigure}{.45\textwidth}
\centering
\includegraphics[scale=0.50]{membership/special4to5}
\caption{
Adding one server to a 4-server cluster.
}
\end{subfigure}
~
\begin{subfigure}{.45\textwidth}
\centering
\includegraphics[scale=0.50]{membership/special3to4}
\caption{
Adding one server to a 3-server cluster.
}
\end{subfigure}

\vspace{3ex}

\begin{subfigure}{.45\textwidth}
\centering
\includegraphics[scale=0.50]{membership/special5to4}
\caption{
Removing one server from a 5-server cluster.
}
\end{subfigure}
~
\begin{subfigure}{.45\textwidth}
\centering
\includegraphics[scale=0.50]{membership/special4to3}
\caption{
Removing one server from a 4-server cluster.
}
\end{subfigure}

\vcaption[adding/removing one server maintains overlap]{
The addition and removal of a single server from an even- and an
odd-sized cluster.
In each figure,
the blue rectangle shows a majority of the old cluster, and the red
rectangle shows a majority of the new cluster.
In every single-server membership change, an overlap between any majority
of the old cluster and any majority of the new cluster is preserved,
as needed for safety. For example in (b), a majority of the old cluster
must include two of the left three servers, and a majority of the new
cluster must include three of the servers in the new cluster, of which
at least two must come from the old cluster.
}
\label{fig:membership:special}
\end{figure}

Most membership change algorithms introduce additional mechanism to deal
with such problems. This is what we did for Raft initially, but we later
discovered a simpler approach, which is to disallow membership changes
that could result in disjoint majorities. Thus, Raft restricts the types
of changes that are allowed: only one server can be added or removed
from the cluster at a time. More complex changes in membership are
implemented as a series of single-server changes. Most of this chapter
describes the single-server approach, which is easier to understand than
our original approach. For completeness,
Section~\ref{membership:arbitrary} describes the original approach,
which incurs additional complexity to handle arbitrary configuration
changes. We implemented the more complex approach in LogCabin prior to
discovering the simpler single-server change approach; it still uses the
more complex approach at the time of this writing.

When adding a single server to a cluster or removing a single server
from a cluster, any majority of the old cluster overlaps with any
majority of the new cluster; see Figure~\ref{fig:membership:special}.
This overlap prevents the cluster from splitting into two independent
majorities; in terms of the safety argument of
Section~\ref{basicraft:safety:argument}, it guarantees the existence of
``the voter''. Thus, when adding or removing just a single server, it is
safe to switch directly to the new configuration. Raft exploits this
property to change cluster membership safely using little additional
mechanism.

Cluster configurations are stored and communicated using special entries
in the replicated log.
This leverages the existing mechanisms in Raft to
replicate and persist configuration information.
It also allows the cluster to continue to service
client requests while configuration changes are in progress,
by imposing ordering between
configuration changes and client requests (while allowing both to be
replicated concurrently in a pipeline and/or in batches).

When the leader receives a request to add or remove a server from its
current configuration (\cold{}), it appends the new configuration
(\cnew{}) as an entry in its log and replicates that entry using the
normal Raft mechanism. The new configuration takes effect on each server
as soon as it is added to that server's log: the \cnew{} entry is
replicated to the \cnew{} servers, and a majority of the new
configuration is used to determine the \cnew{} entry's commitment. This
means that servers do not wait for configuration entries to be
committed, and each server always uses the latest configuration found in
its log.

The configuration change is complete once the \cnew{} entry is
committed. At this point, the leader knows that a majority of the
\cnew{} servers have adopted \cnew{}. It also knows that any servers
that have not moved to \cnew{} can no longer form a majority of the
cluster, and servers without \cnew{} cannot be elected leader.
Commitment of \cnew{} allows three things to continue:
%
\begin{enumerate}
%
\item The leader can acknowledge the successful completion of the
configuration change.
%
\item If the configuration change removed a server, that server can be
shut down.
%
\item Further configuration changes can be started. Before this point,
overlapped configuration changes could degrade to unsafe situations
like the one in Figure~\ref{fig:membership:reconfigurationdifficulty}.
%
\end{enumerate}

As stated above, servers always use the latest configuration in their
logs, regardless of whether that configuration entry has been committed.
This allows leaders to easily avoid overlapping configuration changes
(the third item above), by not beginning a new change until the previous
change's entry has committed. It is only safe to start another membership
change once a majority of the old cluster has moved to operating under
the rules of \cnew{}. If servers adopted \cnew{} only when they
learned that \cnew{} was committed, Raft leaders would have a difficult
time knowing when a majority of the old cluster had adopted it. They
would need to track which servers know of the entry's commitment, and
the servers would need to persist their commit index to disk; neither of
these mechanisms is required in Raft. Instead, each server
adopts \cnew{} as soon as that entry exists in its log, and the leader
knows it's safe to allow further configuration changes as soon as the
\cnew{} entry has been committed. Unfortunately, this decision does
imply that a log entry for a configuration change can be removed (if
leadership changes); in this case, a server must be prepared to fall
back to the previous configuration in its log.

In Raft, it is the caller's configuration that is used in reaching
consensus, both for voting and for log replication:
%
\begin{itemize}
%
\item A server accepts AppendEntries requests from a leader that
is not part of the server's latest configuration. Otherwise, a new server
could never be added to the cluster (it would never accept any log entries
preceding the configuration entry that adds the server).
%
\item A server also grants its vote to a candidate that is not
part of the server's latest configuration (if the candidate has a
sufficiently up-to-date log and a current term). This vote may
occasionally be needed to keep the cluster available. For example,
consider adding a fourth server to a three-server cluster. If one server
were to fail, the new server's vote would be needed to form a majority
and elect a leader.
%
\end{itemize}
%
Thus, servers process incoming RPC requests without consulting their
current configurations.


\documentclass[12pt, a4paper, footexclude, headexclude]{scrartcl}

%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% Packages
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
\usepackage[margin=0.5in]{geometry}

\usepackage[ngerman]{babel}
\usepackage{xcolor}
\usepackage[pdftex]{hyperref}
\usepackage{multicol}

\usepackage{xinttools}
\usepackage[nomessages]{fp}
\usepackage{tabularx}
\usepackage{tcolorbox}

\setlength{\parindent}{0pt}

\usepackage[pdftex]{insdljs}

%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% Parameter
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
\def\fieldWidth{9}
\def\fieldHeight{9}

%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% Javascript
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
\begin{insDLJS}[]{JSDateiname}{Sudoku}

const GAME_DESC = "Sudoku is a logic-based number-placement puzzle.\
The objective is to fill all empty spots with a digit from 1 to 9,\
while the placements needs to follow these rules:\
1. Each row can only contain each digit once\
2. Each column can only contain each digit once\
3. Each 3x3 block can only contain each digit once.";

% Outside variables
const FIELD_WIDTH = AFMakeNumber(\fieldWidth);
const FIELD_HEIGHT = AFMakeNumber(\fieldHeight);
const SCREEN_TEXT_WIDTH = 300;

% Constants
const NUMBERS = 9;
const BOX_WIDTH = 3;
const EMPTY = 0;

% Globals
% Field for current visualisation and input
var complField = new Array();
% The complete field with applied solution
var solution = new Array();
% The field containing only the initial values
var original = new Array();

% Switch if the user wants to input a sudoku
var customMode = false;

% Color data
const COLORS = new Array(
    [ "RGB", 1.0, 1.0, 1.0 ], % white
    [ "RGB", 0.8, 0.8, 0.8 ], % gray
    [ "RGB", 0.203, 0.603, 0.054 ], % green
    [ "RGB", 0.660, 0.178, 0.233 ], % red
    [ "RGB", 0.078, 0.305, 0.560 ]
);

%%%%%%%%%%
% Helper %
%%%%%%%%%%
/**
 * Returns a random number between 0 and the param.
 * @param {Number} max The upperbound
 */
function getRandomInt(max) {
    return Math.floor(Math.random() * max);
}

/**
 * Shuffles array in place.
 * https://stackoverflow.com/questions/6274339/how-can-i-shuffle-an-array
 *
 * @param {Array} a items An array containing the items.
 */
function shuffle(a) {
    var j, x, i;
    for (i = a.length - 1; i > 0; i--) {
        j = Math.floor(Math.random() * (i + 1));
        x = a[i];
        a[i] = a[j];
        a[j] = x;
    }
    return a;
}

%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% Initialisation and Restart %
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
/**
 * Initialise the default game state by clearing everything and
 * generating a sudoku.
 */
function initialise() {
    % Initlialise all arrays with a zero array
    for (var row = 0; row < FIELD_HEIGHT; row++) {
        var zArr1 = new Array();
        var zArr2 = new Array();
        var zArr3 = new Array();
        for (var column = 0; column < FIELD_WIDTH; column++) {
            zArr1.push(EMPTY);
            zArr2.push(EMPTY);
            zArr3.push(EMPTY);
        }
        complField.push(zArr1);
        solution.push(zArr2);
        original.push(zArr3);
    }

    % Init the GUI
    initialiseButtons();

    generateSudoku();
}

/**
 * Initialise all buttons from the GUI.
 * For example add callbacks and set the correct colors.
 */
function initialiseButtons() {
    % Assign each button the coresponding function and disable the highlights
    this.getField("generate").setAction("MouseUp", "generateSudoku();");
    this.getField("generate").highlight="none";
    this.getField("hint").setAction("MouseUp", "showHint();");
    this.getField("hint").highlight="none";
    this.getField("solve").setAction("MouseUp", "showSolution();");
    this.getField("solve").highlight="none";
    this.getField("enter").setAction("MouseUp", "enterSudoku();");
    this.getField("enter").highlight="none";
    this.getField("reset").setAction("MouseUp", "resetSudoku();");
    this.getField("reset").highlight="none";

    % Selection field for the amount of predefined fields when generating
    this.getField("elemcount").borderColor = color.white;
    this.getField("elemcount").currentValueIndices = 2;
    this.getField("elemcount").commitOnSelChange = true;

    % Each field needs to be connected to an input function
    % Define text style
    var funcName = "checkInput";
    for (var x = 0; x < FIELD_WIDTH; x++) {
        for (var y = 0; y < FIELD_HEIGHT; y++) {
            var callbackName = funcName + "(" + x.toString() + "," + y.toString() + ");";
            this.getField("pos" + x + "-" + y).setAction("OnBlur", callbackName);
            this.getField("pos" + x + "-" + y).textSize = SCREEN_TEXT_WIDTH / FIELD_WIDTH;
            this.getField("pos" + x + "-" + y).alignment = "center";
        }
    }

    % Info field setup
    this.getField("info").fillColor = color.transparent;
    this.getField("info").borderColor = color.transparent;

    % Tooltip setup
    this.getField("tooltipbtn").setAction("MouseDown", "tooltip(true);");
    this.getField("tooltipbtn").setAction("MouseUp", "tooltip(false);");
    this.getField("tooltipbtn").highlight="none";
}

/**
 * Enable or disable the tooltip
 *
 * @param {Boolean} on Enable or disable tooltip
 */
function tooltip(on) {
    if (on) {
        % Move the tooltip field to the center of the screen
        % and adjust the size so the text can be displayed
        var field = this.getField("tooltiptxt");
        field.delay = true;
        field.value = GAME_DESC;

        field.multiline = true;
        field.textSize = 16;
        field.fillColor = color.gray;
        % hight 842, width 596
        % upper-left x, upper-left y, lower-right x and lower-right y
        field.rect = [128, 601, 468, 401];

        field.delay = false;
    } else {
        % Remove the field such that it is not visible
        var field = this.getField("tooltiptxt");
        field.delay = true;
        field.value = "";

        field.multiline = false;
        field.fillColor = color.gray;
        field.rect = [0, 0, 0, 0];

        field.delay = false;
    }
}

/**
 * Activate manual sudoku input.
 */
function enterSudoku() {
    % Clear all arrays to zero
    for (var x = 0; x < FIELD_WIDTH; x++) {
        for (var y = 0; y < FIELD_HEIGHT; y++) {
            complField[y][x] = EMPTY;
            solution[y][x] = EMPTY;
            original[y][x] = EMPTY;
        }
    }

    % Save the input mode
    customMode = true;

    drawAll(false);
}

%%%%%%%%%%%%%%%%%%%%%%%%%%
% Generation and solving %
%%%%%%%%%%%%%%%%%%%%%%%%%%
/**
 * Generates a sudoku.
 * The solution is saved inside the solution array.
 * Inside the complField the same values can be found
 * with some of them removed. The amount is defined by
 * the gui element "elemcount".
 *
 * Algorithm:
 * 1. Clear array
 * 2. Fill diagonal 3x3 matrices randomly.
 * 3. Fill rest by solving the sudoku.
 * 4. Remove K elements randomly
 * Source: https://www.geeksforgeeks.org/program-sudoku-generator/
 */
function generateSudoku() {
    customMode = false;

    % Clear array
    for (var x = 0; x < FIELD_WIDTH; x++) {
        for (var y = 0; y < FIELD_HEIGHT; y++) {
            complField[y][x] = EMPTY;
        }
    }

    % Fill all the diagonal 3x3 matrices randomly.
    var numberArray = [];
    for (var i = 1; i <= NUMBERS; i++) {
        numberArray.push(i);
    }

    % % Fill top left
    fillQuad(numberArray, 0, 0);
    % Fill middle
    fillQuad(numberArray, BOX_WIDTH, BOX_WIDTH);
    % Fill bot right
    fillQuad(numberArray, BOX_WIDTH * 2, BOX_WIDTH * 2);

    % Fill rest of the non-diagonal matrices.
    % For every cell to be filled, try all numbers until
    % a safe number is found.
    if (!solveSudoku()) {
        return;
    }

    % Remove K elements randomly
    % Get all possible position combinations
    var positions = [];
    for (var x = 0; x < NUMBERS; x++) {
        for (var y = 0; y < NUMBERS; y++) {
            positions.push([x, y]);
        }
    }
    var num_elements = this.getField("elemcount").value;
    var rnd = 0;
    for (var count = NUMBERS * NUMBERS; count > num_elements; count--) {
        % Draw and remove one random element from the positions array
        rnd = getRandomInt(positions.length);
        var elem = positions[rnd];
        complField[elem[1]][elem[0]] = EMPTY;
        positions.splice(rnd, 1);
    }

    % Save the current field into the original array,
    % to allow for easy reset
    for (var x = 0; x < FIELD_WIDTH; x++) {
        for (var y = 0; y < FIELD_HEIGHT; y++) {
            original[y][x] = complField[y][x];
        }
    }

    drawAll(true);

    printInfoText("Please fill the sudoku.");
}

/**
 * Fills a 3x3 matrix with the number array that is given.
 * The number array is shuffled inside the function to
 * achieve randomness.
 *
 * @param {Array} numberArray Array of numbers to fill the quad with
 * @param {Number} offsetX Select the x position of the quad
 * @param {Number} offsetY Select the y position of the quad
 */
function fillQuad(numberArray, offsetX, offsetY) {
    shuffle(numberArray);

    var x = 0;
    var y = 0;
    % Assign each number to a field
    for (var idx = 0; idx < numberArray.length; idx++) {
        % Wrap to next line - expects the lines to be 3 in length
        x = offsetX + (idx \% BOX_WIDTH);
        y = offsetY + Math.floor(idx / BOX_WIDTH);
        complField[y][x] = numberArray[idx];
    }
}

/**
 * Solve the sudoku.
 *
 * Algorithm:
 * 1. Make list of all empty spaces
 * 2. For each element in list find all candidates
 * 3. Setup an array to save which combinations where tried
 * 4. Iterate all spaces
 * 4.1. Try a candidate
 * 4.2. If field is still valid continue
 * 4.3. Else increase iteration counter and reset spaceiterator
 *
 * @return { Boolean } true if sucessfull, else false
 */
function solveSudoku() {
    % Make list of all empty spaces
    var spaces = getEmptySpaces();

    % For each element in list find all candidates
    var candidates = getCandidates(spaces);

    % This should not happen
    for (var idx = 0; idx < spaces.length; idx++) {
        if (candidates[idx].length == 0) {
            printInfoText("An error occurred in solveSudoku candidates.");
            return false;
        }
    }

    % Setup and init candidate indices
    var indices = [];
    for (var i = 0; i < spaces.length; i++) {
        indices.push(0);
    }

    % Apply candidates
    for (var idx = 0; idx < spaces.length; idx++) {
        complField[spaces[idx][1]][spaces[idx][0]] = candidates[idx][indices[idx]];

        % When the field is not valid increase indices and reset complField and idx
        if (!isFieldValid(spaces[idx][0], spaces[idx][1])) {

            var tmpIdx = idx;
            % Increment the current index
            indices[tmpIdx]++;
            % This allows for checking all combinations:
            % If there is an overflow for the current index it is reset
            % and the idx - 1 is increased until a combination without
            % overflow is found
            for (; indices[tmpIdx] >= candidates[tmpIdx].length; tmpIdx--) {
                indices[tmpIdx] = 0;

                if (tmpIdx - 1 < 0) {
                    printInfoText("An error occurred in solveSudoku comb-check.");
                    return false;
                } else {
                    indices[tmpIdx - 1]++;
                }
            }

            % Reverse not valid solution
            for (var idx2 = 0; idx2 <= idx; idx2++) {
                complField[spaces[idx2][1]][spaces[idx2][0]] = EMPTY;
            }

            % Restart the idx counter since the solution for the spaces did not work
            idx = -1;
        }
    }

    % Save complete solution since we already generated it here
    for (var x = 0; x < FIELD_WIDTH; x++) {
        for (var y = 0; y < FIELD_HEIGHT; y++) {
            solution[y][x] = complField[y][x];
        }
    }

    return true;
}

/**
 * Returns an array of positions ([x, y]) at which
 * the complField contains a zero (0) and is therefore EMPTY.
 *
 * @return {Array} Array of empty spaces
 */
function getEmptySpaces() {
    var spaces = [];
    for (var x = 0; x < FIELD_WIDTH; x++) {
        for (var y = 0; y < FIELD_HEIGHT; y++) {
            if (complField[y][x] == EMPTY) {
                spaces.push([x, y]);
            }
        }
    }
    return spaces;
}

/**
 * Returns an array of candidates which number of 1-9 could be
 * put at the given spaces. These are selected by consulting the
 * typical sudoku rules.
 *
 * @param {Array} spaces An array of empty spots
 * @return {Array} An array of candidates for each space
 */
function getCandidates(spaces) {
    % Helper array to mark all numbers that are disallowed
    var disallowed = [];
    for (var i = 0; i < 9; i++) {
        disallowed.push(true);
    }

    var candidates = [];
    var num = 0;
    % Iterate all spaces that need to be filled
    for (var idx = 0; idx < spaces.length; idx++) {
        % Check the row for all numbers that are set
        for (var x = 0; x < FIELD_WIDTH; x++) {
            num = complField[spaces[idx][1]][x];
            if (num > EMPTY) {
                disallowed[num - 1] = false;
            }
        }

        % Check the column for all numbers that are set
        for (var y = 0; y < FIELD_HEIGHT; y++) {
            num = complField[y][spaces[idx][0]];
            if (num > EMPTY) {
                disallowed[num - 1] = false;
            }
        }

        % Check the box for all numbers that are set
        var xQuad = Math.floor(spaces[idx][0] / BOX_WIDTH);
        var yQuad = Math.floor(spaces[idx][1] / BOX_WIDTH);
        for (var x = xQuad * BOX_WIDTH; x < xQuad * BOX_WIDTH + BOX_WIDTH; x++) {
            for (var y = yQuad * BOX_WIDTH; y < yQuad * BOX_WIDTH + BOX_WIDTH; y++) {
                num = complField[y][x];
                if (num > EMPTY) {
                    disallowed[num - 1] = false;
                }
            }
        }

        % Get candidates
        var tmpCnd = [];
        for (var i = 0; i < disallowed.length; i++) {
            if (disallowed[i]) {
                tmpCnd.push(i + 1);
            }
        }
        candidates.push(tmpCnd);

        % Reset the disallowed numbers
        for (var i = 0; i < 9; i++) {
            disallowed[i] = true;
        }
    }
    return candidates;
}

/**
 * Checks the field at the given position
 * if there are any conflicts with the sudoku rules
 * given the current numbers in the field.
 *
 * @param {Number} valX X-coordinate of the field
 * @param {Number} valY Y-coordinate of the field
 * @return {Boolean} Returns true if field is valid else false.
 */
function isFieldValid(valX, valY) {
    % Get the value
    var value = complField[valY][valX];

    % Check all possibly conflicting fields for the same value
    % Check the row
    for (var x = 0; x < FIELD_WIDTH; x++) {
        if (complField[valY][x] == value && x != valX) {
            return false;
        }
    }

    % Check the column
    for (var y = 0; y < FIELD_HEIGHT; y++) {
        if (complField[y][valX] == value && y != valY) {
            return false;
        }
    }

    % Check the box
    var xQuad = Math.floor(valX / BOX_WIDTH);
    var yQuad = Math.floor(valY / BOX_WIDTH);
    for (var x = xQuad * BOX_WIDTH; x < xQuad * BOX_WIDTH + BOX_WIDTH; x++) {
        for (var y = yQuad * BOX_WIDTH; y < yQuad * BOX_WIDTH + BOX_WIDTH; y++) {
            if (complField[y][x] == value && (y != valY || x != valX)) {
                return false;
            }
        }
    }

    return true;
}

/**
 * Checks the given user input if it is valid.
 * Needs to be a number betwenn 0 and 10.
 * If the value is not allowed by the sudoku rules
 * the field is marked red and green otherwise.
 *
 * @param {Number} x X-coordinate
 * @param {Number} y Y-coordinate
 */
function checkInput(x, y) {
    % Get the value that was commited
    var field = this.getField("pos" + x + "-" + y);

    % If the value did not change dont do anything
    if (complField[y][x] == field.value) {
        return;
    }
    field.delay = true;

    % When the value is inside the bounds
    % validate it and color the field correspondingly.
    if (field.value > 0 && field.value < 10) {
        complField[y][x] = field.value;
        if (isFieldValid(x, y)) {
            field.fillColor = COLORS[2];
        } else {
            field.fillColor = COLORS[3];
        }
    }
    % Else remove the value from the field
    else {
        field.value = "";
        field.fillColor = COLORS[0];
    }

    field.delay = false;
}

%%%%%%%%%%%%%%%%%%%%%
% Draw and coloring %
%%%%%%%%%%%%%%%%%%%%%
/**
 * Resets the sudoku to the original generated one.
 */
function resetSudoku() {
    for (var x = 0; x < FIELD_WIDTH; x++) {
        for (var y = 0; y < FIELD_HEIGHT; y++) {
            complField[y][x] = original[y][x];
            refreshField(x, y, COLORS[1]);
        }
    }
}

/**
 * Shows one field that was not previously revealed.
 */
function showHint() {
    % If one field in the solution array is zero (EMPTY) the whole array should be
    % zero and therefore the solution was not yet generated
    if (solution[0][0] == EMPTY) {
        solveSudoku();
    }

    for (var x = 0; x < FIELD_WIDTH; x++) {
        for (var y = 0; y < FIELD_HEIGHT; y++) {
            if (complField[y][x] == EMPTY) {
                complField[y][x] = solution[y][x];
                refreshField(x, y, COLORS[1]);
                return;
            }
        }
    }
}

/**
 * Reveals the complete solution.
 */
function showSolution() {
    % When in custom mode it is not possible to know when
    % the user is done therefore the solution can only be
    % generated after requesting it
    if (customMode) {
        solveSudoku();
    }

    % Just copy all values from the solution array
    for (var x = 0; x < FIELD_WIDTH; x++) {
        for (var y = 0; y < FIELD_HEIGHT; y++) {
            if (complField[y][x] == EMPTY || customMode) {
                complField[y][x] = solution[y][x];
                refreshField(x, y, COLORS[0]);
            }
        }
    }
}

/**
 * Refreshes value of one input field
 *
 * @param {Number} x The x position.
 * @param {Number} y The y position.
 * @param {Array} color The rgb color.
 *              Gray for given fields, green for correct fields,
 *              Red for wrong fields, white for empty fields.
 */
function refreshField(x, y, color) {
    var field = this.getField("pos" + x + "-" + y);
    field.delay = true;
    if (complField[y][x] > EMPTY) {
        field.value = complField[y][x];
        field.fillColor = color;
    } else {
        field.value = "";
        field.fillColor = COLORS[0];
    }
    field.delay = false;
}

/**
 * ReDraw complete field, coloring can be enabled.
 *
 * @param {Boolean} color Should the fields be colored.
 */
function drawAll(color) {
    for (var x = 0; x < FIELD_WIDTH; x++) {
        for (var y = 0; y < FIELD_HEIGHT; y++) {
            field = this.getField("pos" + x + "-" + y);
            field.delay = true;
            if (complField[y][x] > EMPTY) {
                field.value = complField[y][x];
                if (color) {
                    field.fillColor = COLORS[1];
                    field.readonly = true;
                }
            } else {
                field.value = "";
                field.fillColor = COLORS[0];
                field.readonly = false;
            }
            field.delay = false;
        }
    }
}

/**
 * Print information about the game.
 *
 * @param {String} text Info string
 */
function printInfoText(text) {
    var field = this.getField("info");
    field.delay = true;
    field.value = text;
    field.delay = false;
}

\end{insDLJS}

\OpenAction{/S /JavaScript /JS (initialise();)}

%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% Dokument
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
\begin{document}

    \begin{Form}

        % Header
        \begin{multicols}{2}
            % Title
            \section*{Sudoku}
        \columnbreak
            % Tooltip object
            \begin{flushright}%
                \PushButton[name=tooltipbtn, bordercolor=white]{%
                    \begin{tcolorbox}[width=20pt, height=20pt, left=3pt, top=0pt]
                        \centering?\strut{}
                    \end{tcolorbox}%
                }
            \end{flushright}%
        \end{multicols}

        % Calculate the max width and height of a block
        \FPeval{\resultW}{(\fieldWidth * 4 + 3 + \fieldWidth * 3)}
        \def\blocksizeW{\dimexpr (\linewidth-\resultW pt)/\fieldWidth \relax}

        \FPeval{\resultH}{(\fieldHeight * 4 + 3)}
        \def\blocksizeH{\dimexpr (500 pt -\resultH pt)/\fieldHeight \relax}

        % Define the blocksize via the smaller amount
        \ifnum\blocksizeW<\blocksizeH
            \def\blocksize{\blocksizeW}
        \else
            \def\blocksize{\blocksizeH}
        \fi

        % Playingfield
        \begin{tcolorbox}
            \begin{flushright}
                \xintFor* #2 in {\xintSeq{0}{\fieldHeight-1}} \do {%
                        \ifnum#2=3%
                            \vspace{-12pt}%
                            \noindent\rule[13pt]{\linewidth}{1pt}
                        \fi%
                        \ifnum#2=6%
                            \vspace{-12pt}%
                            \noindent\rule[13pt]{\linewidth}{1pt}
                        \fi%
                    \vspace{1pt}%
                    \xintFor* #1 in {\xintSeq{0}{\fieldWidth-1}} \do {%
                        \TextField[%
                            width=\blocksize, height=\blocksize,%
                            bordercolor=white, name=pos#1-#2]{}%
                        %
                        \hspace{2pt}%
                        \ifnum#1=2%
                            %\vspace{1pt}%
                            \vrule width 1pt%
                        \fi%
                        \ifnum#1=5%
                            %\vspace{1pt}%
                            \vrule width 1pt%
                        \fi%
                        \hspace{2pt}%
                    }\vspace{1pt}%
                    \newline%
                }%
            \end{flushright}%
        \end{tcolorbox}
        %
        %%%%%%%%%%%%%%%%%%%%%%%
        % Commandredifinition %
        % https://www.dickimaw-books.com/latex/admin/html/eforms.shtml
        %%%%%%%%%%%%%%%%%%%%%%%
        \def\DefaultHeightofText{14pt}
        \renewcommand*{\LayoutTextField}[2]{%
            \parbox[c][\DefaultHeightofText]{\linewidth}{#1#2}%
        }

        \renewcommand*{\DefaultWidthofChoiceMenu}{2.5ex}
        \renewcommand*{\DefaultHeightofChoiceMenu}{2.04ex}

        %%%%%%%%%%%%%%%%
        % GUI elements %
        %%%%%%%%%%%%%%%
        \ChoiceMenu[name=elemcount, bordercolor=gray, width=50mm, combo]
            {Fullfield count:}{15, 30, 45, 60, 75}
        \TextField[bordercolor=white, name=tooltiptxt, readonly=true]{}
        %
        \begin{center}%
            \begin{tabularx}{\textwidth}{@{} *{2}{X} @{}}%
                \PushButton[name=generate, bordercolor=white]{
                    \begin{tcolorbox}
                        \centering
                        Generate new Sudoku\strut
                    \end{tcolorbox}
                } &
                \PushButton[name=enter, bordercolor=white]{
                    \begin{tcolorbox}
                        \centering
                        Enter own Sudoku\strut
                    \end{tcolorbox}
                } \\
                \PushButton[name=solve, bordercolor=white]{
                    \begin{tcolorbox}
                        \centering
                        Show current solution\strut
                    \end{tcolorbox}
                } &
                \PushButton[name=hint, bordercolor=white]{
                    \begin{tcolorbox}
                        \centering
                        Give me a hint\strut
                    \end{tcolorbox}
                } \\
                \PushButton[name=reset, bordercolor=white]{
                    \begin{tcolorbox}
                        \centering
                        Reset current input\strut
                    \end{tcolorbox}
                } &
                \begin{tcolorbox}
                    \TextField[name=info, width=\linewidth, readonly=true]{}
                \end{tcolorbox}
            \end{tabularx}
        \end{center}

    \end{Form}
\end{document}


\subsection{Multiple Additive Regression Trees (MART)}


\documentclass[12pt,letterpaper]{article}

\usepackage{amsmath, amsthm, amsfonts, amssymb}
\usepackage{microtype, parskip, graphicx}
\usepackage{multirow, morefloats, rotating}
\usepackage{caption, subcaption}
\usepackage{lineno}
\usepackage{afterpage}
\usepackage{hyperref}

\title{Report on Fossil/Not Fossil}

\begin{document}
\maketitle

\section{Set-Up}

We want to predict the expected diversity of a Macrostrat geological unit. We are focused on the diversity of individual biological classes. Geological units are described in terms of their lithological descriptions, areal extent, location, ``connectedness'' (units above/below), and other values. Lithological description is a compositional variable and thus has annoying properties which can prove difficult to interpret.

The dataset is split into two sets: the late Ordovician (460.4--445.6) and the Hirnantian (445.6--443.8); the former is the training dataset while the latter is the testing dataset.

\section{Model}

The basics of the models used in this analysis is a hurdle model which is a mixture of a Bernoulli distribution and either a Poisson or Negative-Binomial distribution. The Bernoulli aspect describes the probability of observing 0 species in a geological unit, while the Poisson or Negative-Binomial describes the expected number of species present in that geological unit if there are more than 0.

Both parts of the mixture are modeled as regressions with all of the geological unit covariates as predictors.

The models are fit to the training dataset and the results of which are used to predict the diversity of the Hirnantian geological units. The approximate expected out-of-sample predictions were evaluated through 5 rounds of 5-fold cross-validation.

The models are fit in a fully Bayesian context using the Stan probabilistic programming language. Model fit for the complete training dataset is evaluated through a series of posterior predictive checks. Additionally, models are compared using WAIC and LOOIC which are estimates of comparative out-of-sample predictive performance.

\section{Results}

\subsection{Full data posterior predictive checks}
figures \ref{fig:ppc_mean}, \ref{fig:ppc_sd}, \ref{fig:ppc_ecdf}, \ref{fig:ppc_root}, \ref{fig:ppc_avgerr}. waic \ref{tab:waic} and looic \ref{tab:loo}.

\afterpage{\clearpage}
\begin{figure}[h]
  \centering
  \includegraphics[width=\textwidth,height=0.8\textheight,keepaspectratio=true]{figure/ppc_mean}
  \caption{Mean of unit diversity. Distribution is estimated from posterior, vertical line is observed. Columns are by model type, rows are by taxonomic group.}
  \label{fig:ppc_mean}
\end{figure}

\afterpage{\clearpage}
\begin{figure}[h]
  \centering
  \includegraphics[width=\textwidth,height=0.8\textheight,keepaspectratio=true]{figure/ppc_sd}
  \caption{Standard deviation of unit diversity. Distribution is estimated from posterior, vertical line is observed. Columns are by model type, rows are by taxonomic group.}
  \label{fig:ppc_sd}
\end{figure}

\afterpage{\clearpage}
\begin{figure}[h]
  \centering
  \includegraphics[width=\textwidth,height=0.8\textheight,keepaspectratio=true]{figure/ppc_ecdf}
  \caption{Empirical cumulative distribution function of unit diversity; that is, rank order proportional accumulation. Distribution is estimated from posterior, dark line is observed. Columns are by model type, rows are by taxonomic group.}
  \label{fig:ppc_ecdf}
\end{figure}

\afterpage{\clearpage}
\begin{figure}[h]
  \centering
  \includegraphics[width=\textwidth,height=0.8\textheight,keepaspectratio=true]{figure/ppc_root}
  \caption{Rootogram of unit diversity. Distribution is estimated from posterior, hanging histogram is is observed. If histogram is above x-axis, overestimate; if histogram is below x-axis, underestimate. Columns are by model type, rows are by taxonomic group.}
  \label{fig:ppc_root}
\end{figure}

\afterpage{\clearpage}
\begin{figure}[h]
  \centering
  \includegraphics[width=\textwidth,height=0.8\textheight,keepaspectratio=true]{figure/ppc_avgerr}
  \caption{Average error of estimated unit diversity. Comparison is between observed diversity and estimated diversity. Columns are by model type, rows are by taxonomic group.}
  \label{fig:ppc_avgerr}
\end{figure}

\begin{sidewaystable}
  \centering
  \caption{}
  \label{tab:waic}
  \begin{tabular}{r|llll}
    \hline
    Taxonomic group & Poisson model WAIC & Poisson model SE WAIC & NegBin model WAIC & NegBin model SE WAIC \\
    \hline
    Bivalvia & 1485.42 & 124.66 & 1317.38 & 102.66 \\
    Brachiopoda & 2602.90 & 179.58 & 2134.50 & 123.81 \\
    Gastropoda & 2089.17 & 176.01 & 1636.84 & 114.12 \\
    Trilobita & 1828.36 & 139.25 & 1585.80 & 105.04 \\
    \hline
  \end{tabular}
\end{sidewaystable}

\begin{sidewaystable}
  \centering
  \caption{}
  \label{tab:loo}
  \begin{tabular}{r|llll}
    \hline
    Taxonomic group & Poisson model LOOIC & Poisson model SE LOOIC & NegBin model LOOIC & NegBin model SE LOOIC \\
    \hline
    Bivalvia & 1485.45 & 124.66 & 1319.02 & 102.88 \\
    Brachiopoda & 2602.95 & 179.58 & 2135.65 & 123.91 \\
    Gastropoda & 2089.20 & 176.01 & 1639.43 & 114.45 \\
    Trilobita & 1828.38 & 139.25 & 1586.98 & 105.18 \\
    \hline
  \end{tabular}
\end{sidewaystable}

\subsection{K-fold cross-validation results}
figures \ref{fig:cv_rmse}. CV RMSE estimates \ref{tab:cv_rmse}.

\afterpage{\clearpage}
\begin{figure}[h]
  \centering
  \includegraphics[width=\textwidth,height=0.8\textheight,keepaspectratio=true]{figure/cv_rmse}
  \caption{Posterior estimates of the expected out-of-sample error based on 5 rounds of 5-fold cross-validation. Columns are by model type, rows are by taxonomic group.}
  \label{fig:cv_rmse}
\end{figure}

\begin{sidewaystable}
  \centering
  \caption{}
  \label{tab:cv_rmse}
  \begin{tabular}{rllll}
    \hline
    Taxonomic group & Poisson Model Mean CV RMSE & Poisson Model SD CV RMSE & NegBin Model Mean CV RMSE & NegBin Model SD CV RMSE \\
    \hline
    Bivalvia & 3.51 & 0.13 & 4.18 & 0.08 \\
    Brachiopoda & 7.07 & 0.13 & 7.47 & 0.07 \\
    Gastropoda & 5.23 & 0.15 & 6.37 & 0.17 \\
    Trilobita & 3.52 & 0.07 & 4.36 & 0.05 \\
    \hline
  \end{tabular}
\end{sidewaystable}

\subsection{Regression coefficients}
figures \ref{fig:arth_coefs}, \ref{fig:brach_coefs}, \ref{fig:mol_coefs}.

\afterpage{\clearpage}
\begin{figure}[h]
  \centering
  \includegraphics[width=\textwidth,height=0.8\textheight,keepaspectratio=true]{figure/arth_coefs}
  \caption{left: coefficients from the arthropod analysis. right: regression coefs for compositional variables back-transformed into composition units. theta is for binomial part (i.e. zeroes), lambda is for poisson or negative binomial part (i.e. non-zeroes)}
  \label{fig:arth_coefs}
\end{figure}

\afterpage{\clearpage}
\begin{figure}[h]
  \centering
  \includegraphics[width=\textwidth,height=0.8\textheight,keepaspectratio=true]{figure/brach_coefs}
  \caption{left: coefficients from the brachiopod analysis. right: regression coefs for compositional variables back-transformed into composition units. theta is for binomial part (i.e. zeroes), lambda is for poisson or negative binomial part (i.e. non-zeroes)}
  \label{fig:brach_coefs}
\end{figure}

\afterpage{\clearpage}
\begin{figure}[h]
  \centering
  \includegraphics[width=\textwidth,height=0.8\textheight,keepaspectratio=true]{figure/mol_coefs}
  \caption{left: coefficients from the mollusc analysis. right: regression coefs for compositional variables back-transformed into composition units. theta is for binomial part (i.e. zeroes), lambda is for poisson or negative binomial part (i.e. non-zeroes)}
  \label{fig:mol_coefs}
\end{figure}

\subsection{Predictive results}
figures \ref{fig:pred_mean}, \ref{fig:pred_sd}, \ref{fig:pred_ecdf}, \ref{fig:pred_root}, \ref{fig:pred_avgerr}. rmse from prediction table \ref{tab:test_rmse}.

\afterpage{\clearpage}
\begin{figure}[h]
  \centering
  \includegraphics[width=\textwidth,height=0.8\textheight,keepaspectratio=true]{figure/pred_mean}
  \caption{Mean of unit diversity for testing dataset. Distribution is estimated from posterior, vertical line is observed. Columns are by model type, rows are by taxonomic group.}
  \label{fig:pred_mean}
\end{figure}

\begin{figure}[h]
  \afterpage{\clearpage}
  \centering
  \includegraphics[width=\textwidth,height=0.8\textheight,keepaspectratio=true]{figure/pred_sd}
  \caption{Standard deviation of unit diversity for testing dataset. Distribution is estimated from posterior, vertical line is observed. Columns are by model type, rows are by taxonomic group.}
  \label{fig:pred_sd}
\end{figure}

\afterpage{\clearpage}
\begin{figure}[h]
  \centering
  \includegraphics[width=\textwidth,height=0.8\textheight,keepaspectratio=true]{figure/pred_ecdf}
  \caption{Empirical cumulative distribution function of unit diversity for testing dataset; that is, rank order proportional accumulation. Distribution is estimated from posterior, dark line is observed. Columns are by model type, rows are by taxonomic group.}
  \label{fig:pred_ecdf}
\end{figure}

\afterpage{\clearpage}
\begin{figure}[h]
  \centering
  \includegraphics[width=\textwidth,height=0.8\textheight,keepaspectratio=true]{figure/pred_root}
  \caption{Rootogram of unit diversity for testing dataset. Distribution is estimated from posterior, hanging histogram is is observed. If histogram is above x-axis, overestimate; if histogram is below x-axis, underestimate. Columns are by model type, rows are by taxonomic group.}
  \label{fig:pred_root}
\end{figure}

\afterpage{\clearpage}
\begin{figure}[h]
  \centering
  \includegraphics[width=\textwidth,height=0.8\textheight,keepaspectratio=true]{figure/pred_avgerr}
  \caption{Average error of estimated unit diversity for testing dataset. Comparison is between observed diversity and estimated diversity. Columns are by model type, rows are by taxonomic group.}
  \label{fig:pred_avgerr}
\end{figure}

\begin{sidewaystable}
  \centering
  \caption{}
  \label{tab:test_rmse}
  \begin{tabular}{r|llll}
    \hline
    Taxonomic group & Poisson model Mean CV RMSE & Poisson model SD CV RMSE & NegBin model Mean CV RMSE & NegBin model SD CV RMSE \\
    \hline
    Bivalvia & 2.21 & 1.30 & 5.11 & 2.89 \\
    Brachiopoda & 5.05 & 3.14 & 7.81 & 6.18 \\
    Gastropoda & 3.24 & 0.89 & 6.37 & 2.20 \\
    Trilobita & 1.81 & 0.99 & 4.18 & 1.07 \\
    \hline
  \end{tabular}
\end{sidewaystable}

\end{document}


\section{Proving Techniques}

The properties that have been proven can be divided into three types: Preconditions, Invariants and Post-conditions \cite{meyer_1992}. Preconditions are properties that must be true before a function is called, post-conditions must be true after a function is called, and invariants are properties that must be true for all values of a certain type. In this section it will be shown that these three types of properties each have their own way to be proven in Agda.

\subsection{Finding properties to prove}\label{finding_props_to_prove}
\cite{BREITNER2021} presents multiple techniques to find properties to prove from Haskell code. A few of those techniques have been selected that were deemed useful for this paper:
\begin{enumerate}
	\item Define an invariant property when there are types whose correctness depend on invariants
		\cite[p. 7]{BREITNER2021}
	\item Define a post-condition property by deriving a definition directly from the test suite
		\cite[p. 9]{BREITNER2021}
	\item Define a precondition when there is a risk of numeric overflow, or switch to using unbounded integers instead.
		\cite[p. 9]{BREITNER2021}
	\item Define a post-condition when there are type classes which come with laws that all instances of the type class should satisfy
		\cite[p. 10]{BREITNER2021}
\end{enumerate}
Finally, one technique that was not mentioned in \cite{BREITNER2021} was used:
\begin{enumerate}
	\setcounter{enumi}{4}
	\item Define a precondition if it is required to make the function total, as was described in section \ref{total-functions}
\end{enumerate}

\subsection{Properties to prove}\label{props_to_prove}

Instead of defining a precondition when there is a risk of numeric overflow as described in technique 3, we switch to using unbounded integers in this papers' implementation of the QuadTree library. This is the same decision that \cite{BREITNER2021} made. Furthermore, the test suite of the QuadTree library consists only of tests that test the type class laws, so no additional properties could be derived from technique 2. Using technique 1, 4, and 5, the following properties of the QuadTree library were derived:

\setlength{\parindent}{0pt} \setlength{\parskip}{5pt}
\textbf{Invariants of a QuadTree:}
\begin{itemize}
    \item Depth invariant: The depth of a QuadTree must be less than or equal to \linebreak $\left \lceil{log_{2}( max(width, height))}\right \rceil$. This is to ensure that there is exactly one value at each location. (Technique 1)
    \item Compression invariant: No node can have four leaves that are identical. These need to be fused into a single leaf quadrant. This is needed to keep the QuadTree fast and space efficient. (Technique 1)
\end{itemize}
\textbf{Preconditions of a QuadTree:}
\begin{itemize}
    \item When calling \verb|atLocation|, \verb|getLocation|, \verb|setLocation| or \verb|mapLocation|, the location must be inside of the QuadTree. (Technique 5)
    \item When calling \verb|lensLeaf|, the quadrant needs to have a depth of zero (i.e.  it must be a leaf) (Technique 5)
    \item When calling \verb|lensA/B/C/D|, the quadrant needs to have a depth that is greater than zero (i.e.  it must not be a leaf) (Technique 5)
\end{itemize}
\textbf{Post-conditions of a QuadTree:}
\begin{itemize}
    \item The lenses returned by all the lens functions satisfy the lens laws: \cite{lens} (Technique 4)
        \begin{itemize}
            \item \verb|view l (set l v s) = v| (Setting and then getting returns the value)
            \item \verb|set l (view l s) s = s| (Setting the value to what it already was doesn't change anything)
            \item \verb|set l v2 (set l v1 s) = set l v2 s| (Setting a value twice is the same as setting it once to the second value)
        \end{itemize}
    \item The functor implementations for Quadrant and QuadTree satisfy the functor laws (Technique 4)
        \begin{itemize}
            \item \verb|fmap id = id| (Identity law)
            \item \verb|fmap (f . g) == fmap f . fmap g| (Composition law)
        \end{itemize}
    \item The foldable implementation returns an output of the correct length (Technique 4)
        \begin{itemize}
            \item \verb|length quadtreeFoldable vqt = width * height|
        \end{itemize}
    \item The foldable implementation satisfies the foldable-functor law (Technique 4)
        \begin{itemize}
            \item \verb|foldMap f = fold . fmap f|
        \end{itemize}
\end{itemize}

\setlength{\parindent}{15pt} \setlength{\parskip}{0pt}
\subsection{Techniques to prove invariants} \label{prove_invariants}
Invariants are proven by creating a new datatype with one constructor, which takes the original datatype and a proof for all the invariants. As a simple example, this datatype represents a natural number with the invariant that it is greater than 5.
\begin{minted}{agda}
data GreaterThanFive : Set where
  CGreaterThanFive : (n : Nat) -> { .( IsTrue (n > 5) ) } -> GreaterThanFive
\end{minted}
The proof is marked as implicit \{\} so that it is removed when compiled to Haskell, and it is marked as as irrelevant .() so that will not interfere when proving post-conditions later. An irrelevant value means that the actual value of the proof does not matter, only its existence does.

Using this technique, the datatype for a compressed quadrant with a certain maximum depth is:
\begin{minted}{agda}
data VQuadrant (t : Set) {depth : Nat} : Set where
  CVQuadrant : (qd : Quadrant t)
            -> {.(IsTrue (depth qd <= depth && isCompressed qd))}
            -> VQuadrant t {depth}
\end{minted}
The datatype for a valid QuadTree is defined very similarly. Agda2hs flawlessly compiles this to the following Haskell code, where the proof is erased:
\begin{minted}{haskell}
data VQuadrant t = CVQuadrant (Quadrant t)
\end{minted}

The advantage of making a new wrapper datatype over adding the proofs to the original datatype is that if the original datatype has multiple constructors, functions that use the proof do not need to be split into multiple cases (one for each constructor). The disadvantage is that this additional wrapper type is visible when compiled to Haskell. To avoid this, it is possible to create an additional function for all public functions. This function then takes the invariance proof as a precondition, and calls the original function with the wrapper type.

\subsection{Techniques to prove preconditions}
In this section, two techniques to prove preconditions are presented.

\subsubsection{Using an implicit argument} \label{using_implicit}
When using the implicit argument technique, preconditions are proven by adding the proofs as implicit arguments to the function.
As a simple example, this function takes a natural number that must be greater than 5.
\begin{minted}{agda}
takesGtFive : (n : Nat) -> { .( IsTrue (n > 5) ) } -> ?
\end{minted}
As with invariants, the proof is marked as implicit and irrelevant.

Using this technique, a precondition can be used to ensure that the location given to the \verb|getLocation| function must be inside the QuadTree:
\begin{minted}{agda}
-- Function that checks if a location is inside a given QuadTree
isInsideQuadTree : (Nat × Nat) -> QuadTree t -> Bool
isInsideQuadTree (x , y) (Wrapper (w , h) _) = x < w && y < h

getLocation : (loc : Nat × Nat) -> (qt : QuadTree t)
    -> {.( IsTrue (isInsideQuadTree loc qt) )} -> t
\end{minted}
After being compiled with Agda2hs, the precondition is removed from the function, just like with invariants.
\begin{minted}{haskell}
getLocation :: (Nat, Nat) -> QuadTree t -> t
\end{minted}

\subsubsection{Using a datatype with invariants}
Another technique to prove preconditions is by passing in a datatype with an invariant, as was used in section \ref{prove_invariants}. The simple example from \ref{using_implicit} would then be written like this, using the type defined in section \ref{prove_invariants}:
\begin{minted}{agda}
takesGtFive : (n : GreaterThanFive) -> ?
\end{minted}

For the QuadTree verification, this technique was used to encode the maximum depth properties of the lens functions, using the same datatype that was defined for the invariants.
\begin{minted}{agda}
lensLeaf : Lens (VQuadrant t {0}) t
lensA : {dep : Nat}
    -> Lens (VQuadrant t {S dep}) (VQuadrant t {dep})
\end{minted}

\subsubsection{Comparison}
The advantages of using implicit arguments is that it is not necessary to define a separate datatype, and that the precondition can be dependent on more than one parameter of the function. On the other hand, the advantages of using a datatype with an invariant is that the defined function are cleaner and more compact. It is then also possible to use the type as a parameter for another type, like it is used in \verb|lensLeaf| and \verb|lensA|. It also allows for cleaner reuse of the property, as it does not need to be repeated each time it is used.

\subsection{Techniques to prove post-conditions}
Post-conditions are proven as separate functions. As a simple example, this is a proof that this function returns a number greater than 5.
\begin{minted}{agda}
gt5 : Bool -> Nat
gt5 _ = 42

gt5-is-gt5 : (b : Bool) -> IsTrue (gt5 b > 5)
gt5-is-gt5 b = IsTrue.itsTrue
\end{minted}

For the QuadTree verification, this technique was used to verify the lens laws of all the lenses defined in the implementation. For example, this is the proof that the ViewSet law holds for \verb|lensLeaf|.
\begin{minted}{agda}
ValidLens-Leaf-ViewSet :
    -> (v : t) (s : VQuadrant t {0})
    -> view (lensLeaf {t}) (set (lensLeaf {t}) v s) ≡ v
ValidLens-Leaf-ViewSet v (CVQuadrant (Leaf x)) = refl
\end{minted}

When proving preconditions and invariants, these properties have to be marked as irrelevant. This is to ensure that when proving that two function calls are equal, one does not need to show that the proofs of the preconditions and invariants are equal, since the actual value of the proofs is irrelevant.

\subsection{Results} \label{results}
All of the properties mentioned in section \ref{props_to_prove} have been successfully proven. Most of these proofs have not been shown in the paper, since they are available in the source code. The amount of lines of code that this took is shown in figure \ref{division}.  This counts all non-empty lines. The verification took about 3 times more lines of code than the implementation. While this comparison is an indication, this should not be taken to mean that the verification took 3 times as much effort, as the information density of the implementation and proofs is different.

In reality, the implementation took approximately one full-time week, while the verification took approximately five full-time weeks. This too should not be taken to mean the verification took 5 times as much effort, as this number may be biased by the fact that the implementation was just a translation from Haskell.

During the verification phase, one bug was found in this papers implementation of QuadTree that was accidentally introduced during the translation to Agda. This was not caught by the tests, though this may be because the tests on the foldable implementation are very limited.

Whether the verification is worth the time spent, depends on the situation. For example, in a situation where even one small error could bring down an airplane, this is clearly worth it. However, in many common situations, this verification may not be worth it.

\begin{figure}[H]
	\begin{tikzpicture}[scale=0.8]
		\pie[sum=auto]
		{757/Implementation,
			545/General Proofs,
			789/Foldable Proofs,
			809/Lens Proofs,
			215/Functor Proofs}
	\end{tikzpicture}
	\caption{Division of lines of code}
	\label{division}
\end{figure}


\section{Results}
The agent was trained for 100000 episodes with random restarts every 20000 episodes. For evaluating the performance the agent average game length, mean \(Q\) value, mean reward, and mean loss is recorded. Results from one random restarts is shown in ~\autoref{fig:results} in~\autoref{app:results}. From the figures we can conclude that the agent improves its knowledge about the game nearly every episode. The graphs are not smoothed out, even tough the trajectory is clearly upwards for received reward, and as the agent explores the reward fluctuates. Lastly, the random agent scores \(1.5\) on average, and the best agent we trained scores 28 on average \(1886\%\) better than taking random actions.


\chapter{Conclusions}\label{concl}
\thispagestyle{plain}

In this thesis three machine learning algorithms have been used to create models aimed at predicting glaciers ice thickness.

In order to do so, the GlaThiDa, a database containing ice thickness observations of glaciers all over the world has been linked to the RGI, a database of glaciers outlines which include over 215,000 glaciers and represents all glaciers and ice caps in the globe. Of all the observations in GlaThiDa, 96.6\% have been associated with glaciers in the RGI, summing up to a total of only 771 glaciers worldwide with ice thickness observations. In many glaciers only few observations have been reported in the GlaThiDa, and some regions completely lack ice thickness measurements.

In order to create a data set to train the machine learning models, the Open Global Glacier Model has been used. This model provided the tools to merge together the relevant digital elevation models for each glacier, and compute gridded geometrical features such as: the topography, the distance from the border of the glacier, the slope angle and the altitude dependent linear mass balance.

With this data three different machine learning models, linear regression, random forest regression and support vector regression, have been trained using only observations available for the alpine region. To avoid over-fitting the models, and to be able to assess their performances, each model has been trained with 20 different sub-samples, each containing 75\% of data points available. The $R^2$ coefficient, also called score, calculated over the resulting 25\% of the data, has been chosen as a value to assess the performances of each model. The best performing model on average was the support vector regression with an average $R^2 = 0.55$. The spread of the score between the models trained with the different sub-samples has been found particularly high with much lower scores for some specific sub-samples. This is true for the three different machine learning algorithms used, as all of them showed drops in score for samples 5, 14 and 19. This behavior could be explained by the fact that the sub-sample left out for training in these 3 cases was particularly hard to predict but might also be a sign of over-fitting.
The model achieving the highest score when training them over the whole sample has been the random forest regression with a score of 0.57.

After the models have been trained the relevance of each feature in the models predictions has been analyzed. The mass balance was the most relevant feature for both the random forest and support vector regression, but for the linear regression it was the slope angle. Those two features however proved to be relevant for the predictions of all the models. Altitude and distance from the border seem to be much less important for the predictions of both the random forest and the linear regression model, while still being relevant for the support vector regression. The importance of mass balance and slope angle in determining the ice thickness of glaciers, is in accordance with the general theory of ice dynamics in glaciers.

The trained machine learning models have been used to estimate the ice thickness of each of the glaciers in the Alps. The results have been compared to those obtained by \citet{Farinotti2019} (F19). All the machine learning models have been found to predict very different volumes compared to the ones predicted in the \citet{Farinotti2019}. The linear regression is the only model which predicted a total ice volume larger than the one from F19 by over 9\%. The random forest and support vector machine predicted a total volume respectively 22\% and 25\% lower than F19. These two models in fact seem to underestimate the ice thickness for large glaciers, leading to low volume values for those glaciers and hence for the whole region. Larger glaciers are essential in estimating the total volume of ice but are also outliers in the per-volume distribution of glaciers in the alps. The machine learning algorithms seem then unfit to make predictions about these larger glaciers. This could be explained by the fact that the models were not able to learn the patterns of these large glaciers, due to the fact that they had no information about them in the training data-set.

When comparing the performances of the machine learning models to those of the single models used by \citet{Farinotti2019}, using the observations as reference, the tendency of the machine learning models to underestimate ice thickness has been furthered confirmed. In contrast two physical models showed an opposite trend predicting larger values more often than lower ones and the other two seem to have low bias in the predictions, predicting equally lower or higher ice thickness values compared to the observations. The reason for the machine learning models underestimating the ice thickness of glaciers is probably related to the training data-set being skewed towards the presence of low ice thickness values.

In conclusion, the machine learning algorithms have not been very accurate in estimating the ice thickness for Alpine glaciers, using the features chosen as input values. This applies particularly to large glaciers, for which the models seem unable to replicate accurate ice thicknesses.

A lot could be done to improve the machine learning models performances.
One of the first thing to try could be the usage of different machine learning algorithms to train the model. An example could be the use of artificial neural networks as in the work of \citet{Clarke2009}, which was however not based on real glacier data but on artificially grown ones. Artificial neural networks have in fact shown a lot of real life applications in the last years due to their accurate performances, and seeing how they would perform on the problem of estimating glacier ice thickness could be very interesting.

Using more and different features could also be a very interesting possibility. Adding the mass balance based on the catchment basins could already be a big improvement on the mass balance used. A smoothed version of this would be ideal but even the non-smoothed one could be beneficial. Even if the ice thickness distribution would look unrealistic, it could still lead to better estimates for glacier volumes. Climate data like precipitation and temperature could also be used as they could be helpful in recognizing differences between glaciers.

Increasing the grid resolution could also improve the models performances. Many measurements have been in fact agglomerated into single ones, due to the fact that they were all falling inside the same grid cell. Having more measurements could give the machine learning algorithms more room to learn. This could however also skew the predictions of the algorithms, as glaciers with many more observations could have a much higher influence in the training process than those with few ones.

Further research could also look into the data from other regions included in the GlaThiDa database.  This thing in particular could lead to models able to predict glaciers ice thickness for those regions, better than the models trained in this thesis. In fact, if the observations for those regions were covering a wider spectrum of ice thickness and feature values, the models could be trained with data better representing the whole distribution of glaciers for the inspected region. As machine learning models can only learn from the data fed to them, those data are in fact extremely important for thje outcome of the prediction.

Finally, the importance of collecting measurements for a wide spectrum of values, is something to be taken into account for the future. A data-set covering the distribution of glaciers as well as possible, is in fact very important for statistical glacier models, but also for the validation of the physically based ones. The importance of this problem could then be taken into consideration, when choosing where to lead future campaigns to collect ice thickness measurements.