\section{Parameterization of model titration}
% - Jack/Ruibin
CpHMD is a relative free energy simulation approach, whereby the potential of mean force (PMF) of deprotonation of
a titratable amino acid in the protein environment is calculated relative to that of a reference, i.e., a model compound or peptide in solution
\cite{Lee_Brooks_2004_Proteins,Khandogin_Brooks_2005_Biophys.J.}.
Model compounds, which were used in the early development of CpHMD methods
\cite{Lee_Brooks_2004_Proteins,Khandogin_Brooks_2005_Biophys.J.,Huang_Shen_2016_J.Chem.TheoryComput.},
are blocked single amino acid residues \ce{CH3CO}-X-\ce{NH2} or \ce{CH3CO}-X-\ce{CONH2},
where X represents a titratable amino acid.
In the development of the hybrid-solvent CpHMD \cite{Wallace_Shen_2011_J.Chem.TheoryComput.} and GBNeck2-CpHMD \cite{Huang_Shen_2018_J.Chem.Inf.Model.,Harris_Shen_2019_J.Chem.Inf.Model.},
model peptides
\ce{CH3CO}-AAXAA-\ce{NH2} were used to take advantage of recent experimental data \cite{Thurlkill_Pace_2006_ProteinSci.,Platzer_McIntosh_2014_J.Biomol.NMR}.
Since in the CpHMD simulation, a model PMF is subtracted,
simulation of a model compound or peptide should return a zero PMF at the pH value equal to the model {\pka}.
In other words, protonated and deprotonated states are sampled with equal probabilities ($S\approx0.5$).
To ensure this is the case, the model PMF needs to be accurately determined.

To obtain the model PMF $U^{\rm mod}$, we use a free energy
simulation method called thermodynamics integration,
in which the mean forces at different values of $\theta$ (for single site titration)
or $\theta$ and $x$ for double site titration
% $\langle\partial U/\partial\theta|_{\theta_i}\rangle$,
are calculated and then analytically
integrated to obtain $U^{\rm mod}$.
The single site titration model is applied
to Cys and Lys. The latter has equivalent protons, so one is selected for titration.
There are two types of double site titration model. His sidechains have two titratable nitrogens with different microscopic {\pka's}, while
carboxylate sidechains (Asp and Glu) have two titratable oxygens but identical microscopic {\pka's}.
These three titration models require
different forms of $U^{\rm mod}$ and methods of fitting.

\subsection{Protocol of parameterization for single site model titration}
For running TI simulations to obtain parameters, we set the options \textbf{prlam} to FALSE, \textbf{prderiv} to TRUE, and \textbf{phtest} to TRUE in the phmdin file, vph{\_}theta to 0 in the phmdstrt file.
For a single site titration model (e.g., Cys and Lys),
we run CpHMD simulations at
$\theta_i=\left(0.4,0.6,0.785,1.0,1.2,1.4\right)$.
Each simulation is run for 10 ns, from which the mean forces
$\langle\partial U/\partial\theta|_{\theta_i}\rangle$
are calculated.
Fitting of the mean forces
to the following analytic form of $\partial U/\partial\theta$ (Eq.~\ref{Eq:dU_dtheta}) returns the two parameters $A$ and $B$ (Fig.~\ref{Fig:parm_cys}).

\begin{equation}
    \frac{\partial U}{\partial\theta}=2A\sin\left(2\theta\right)\left(\sin^{2}\theta-B\right).
    \label{Eq:dU_dtheta}
\end{equation}
As an example, Fig.~\ref{Fig:parm_cys} shows the fitting result for the GBNeck2-CpHMD titration of  Cys model peptide.
We note, fitting should be performed in the $\theta$ space (and not $\lambda$ space) to reduce errors.
 %---------------------------------------------
\begin{figure}[htb!]
    \centering
    \includegraphics[width=3.3in]{figs/cys_parm.pdf}
    \caption{\textbf{Example of fitting A and B parameters for a single site titration model.}
    }
\label{Fig:parm_cys}
\end{figure}
 %---------------------------------------------

\paragraph{Protocol of parameterization for histidine model titration}
For a double site titration model
with two different microscopic \pka's
(e.g. His), the two-dimensional PMF (Eq.~\ref{eq:double}) can be reduced to the
following form
\cite{Khandogin_Brooks_2005_Biophys.J.},

\begin{align}
U^{\rm mod}= & A_{10}\lambda^{2}x^{2}+2\left(A_{1}B_{1}-A_{0}B_{0}\right)\lambda x \nonumber \\ & + 2\left(A_{0}B_{0}-A_{1}B_{1}-A_{10}B_{10}\right)\lambda^{2}x \nonumber \\ & + A_{1}\lambda^{2}-2A_{1}B_{1}\lambda,
\label{eq:PMF_his}
\end{align}
where $\lambda=sin^2\theta$ and $x=sin^2\theta^x$.
The six parameters $A_{0}$, $B_{0}$, $A_{1}$,  $B_{1}$, $A_{10}$, and $B_{10}$ are the parameters
in the quadratic functions
that describe the one-dimensional processes
\cite{Khandogin_Brooks_2005_Biophys.J.}.
$A_0$ and $B_0$ correspond to \ce{HIP <=> HID},
i.e., titration at N$\epsilon$;
$A_1$ and $B_1$ correspond to \ce{HIP <=> HIE},
i.e., titration at N$\delta$;
and $A_{10}$ and $B_{10}$ correspond to the tautomer interconversion \ce{HIE <=> HID}.

\textbf{Step 1.}
To obtain $A_0$ and $B_0$, we
run TI simulations by fixing
$\theta^{x}$ at 0 ($\lambda=0$, HID, N$\delta$ is protonated), varying
$\theta$ at $\left(0.0,0.2,0.4,0.6,\\
0.785,1.0,1.2,1.4,1.5708\right)$, and fitting
the resulting mean forces to the following one-dimensional function,
\begin{equation}
    \frac{\partial U}{\partial\theta}=2A_{0}\sin\left(2\theta\right)\left(\sin^{2}\theta)-B_{0}\right).
\end{equation}

\textbf{Step 2.}
To obtain $A_1$ and $B_1$,
we run TI simulations by fixing
$\theta^{x}$ at 1.5708 ($\lambda=1$, HIE, N$\delta$ is protonated), varying
$\theta$ at $\left(0.0,0.2,0.4,0.6,\\
0.785,1.0,1.2,1.4,1.5708\right)$, and
fitting
 to the following one-dimensional function,
\begin{equation}
    \frac{\partial U}{\partial\theta}=2A_{1}\sin\left(2\theta\right)\left(\sin^{2}\theta-B_{1}\right).
\end{equation}

\textbf{Step 3.}
To obtain $A_{10}$ and $B_{10}$, we run TI simulations by fixing $\theta$ at 1.5708
($\lambda=0$, HIP, doubly protonated His),
varying $\theta_{x}$ at $\left(0.0,0.2,0.4,0.6,0.785,1.0,1.2,1.4,1.5708\right)$
and fitting the resulting mean forces
 to the following one-dimensional function,

\begin{equation}
    \frac{\partial U}{\partial\theta^{x}}=2A_{10}\sin\left(2\theta^{x}\right)\left(\sin^{2}\theta^{x}-B_{10}\right).
\end{equation}

\paragraph{Protocol of parameterization for carboxylic acid model titration}
For double site titration models with two identical microscopic \pka's (e.g., Asp and Glu), the two-dimensional PMF (Eq.~\ref{eq:double})
can be reduced to the following form \cite{Khandogin_Brooks_2005_Biophys.J.},
% Equation...
\begin{equation}
\begin{split}
U^{\rm mod}(\lambda_i,x_i) =
&(R_1 \lambda_i^2 + R_2 \lambda_i + R_3)(x_i + R_4)^2 + R_5 \lambda_i^2 + R_6 \lambda_i
\end{split}\label{eq:carboxyl}
\end{equation}

where $R_1$, ..., $R_6$ are parameters that can be determined via one-dimensional fitting.

%   Determine R1 R2 and R3 by fitting A(lambda) to R1 lambda^2 + R2 lambda + R3
%     R4 = 0.5
%     Determine R5 by fitting A(x) to C1 x^2 + C2 x + R5
%     Determine R6 by fitting B(x) to C1 x^2 + C2 x + R6

\textbf{Step 1.} To generate the data for fitting,
we run TI simulations at the combinations of $\theta$ value of 0.0, 0.4, 0.6, 0.785, 1.0, 1.2, or 1.4
and $\theta^{x}$ value of 0.0, 0.4, 0.6, 0.785, 1.0, 1.2, 1.4, or 1.5708.

\textbf{Step 2.}
We obtain $A$ and $B$ parameters
at each value of $\theta$,
$A(\theta)$ and $B(\theta)$,
by fitting
$\left<\partial U/\partial\theta_{x}\right>$
at different $\theta^x$ values to
the derivative of the quadratic function,
% can be obtained at each value of $\theta$ by fitting $<\partial U/\partial\theta_{x}>$ to
\begin{equation}
    \frac{\partial U}{\partial\theta^{x}}=2A(\theta)\sin\left(2\theta_{x}\right)\left(\sin^{2}\theta_{x}-B(\theta)\right),
\end{equation}
where $A(\theta)$ and $B(\theta)$ are the $\theta$-dependent parameters.

\textbf{Step 3.}
We obtain $A$ and $B$ parameters
at each value of $\theta^x$, $A(\theta^x)$ and $B(\theta^x)$,
by fitting
$\left<\partial U/\partial\theta\right>$
at different $\theta$ values,
% compute $A\left(\theta_{x}\right)$ and $B\left(\theta_{x}\right)$ at each value of $\theta_{x}$ by fitting $\partial U/\partial\theta_{x}$ to

\begin{equation}
    \frac{\partial U}{\partial\theta}=2A(\theta^x)\sin\left(2\theta\right)\left(\sin^{2}\theta-B(\theta^x)\right),
\end{equation}
where $A(\theta^x)$ and $B(\theta^x)$ are the parameters.

\textbf{Step 4.}
We obtain $R_{1}$, $R_{2}$, and $R_{3}$ by fitting $A(\theta_i)$ to

\begin{equation}
    A\left(\theta\right) = R_{1}\sin^{4}\theta + R_{2}\sin^{2}\theta+R_{3},
\end{equation}

\textbf{Step 5.}
We set $R_{4}=0.5$, because the two titrating sites are identical. We then obtain $R_{5}$ by fitting $A(\theta^x)$ to

\begin{equation}
    A\left(\theta^{x}\right)=a_{0}\sin^{4}\theta^{x}+a_{1}\sin^{2}\theta^{x}+R_{5},
\end{equation}
and obtain $R_{6}$ by fitting $B(\theta^x)$ to

\begin{equation}
    B\left(\theta^{x}\right)=a_{0}\sin^{4}\theta^{x}+a_{1}\sin^{2}\theta^{x}+R_{6},
\end{equation}

\subsection{Scripts for TI simulations and parameterization}
To facilitate TI simulations and parameter fitting, we implemented a Shell script
\href{https://gitlab.com/shenlab-amber-cphmd/cphmd-tutorial/-/blob/main/parameterization/scripts/heat_equil_prod_param.sh}{heat\_equil\_prod\_param.sh} and a Python program
\href{
https://gitlab.com/shenlab-amber-cphmd/cphmd-tutorial/-/blob/main/parameterization/scripts/cphmd_parm_fit.py}{cphmd\_parm\_fit.py}.
% The above parameterization settings are included in the heat\_equil\_prod\_param.sh script and the fitting procedure is included in the cphmd\_parm\_fit.py script, both in the parameterization/scripts folder of the \href{https://gitlab.com/shenlab-amber-cphmd/cphmd-tutorial/-/tree/main/parameterization/scripts}{cphmd-tutorial} gitlab repository.
Here we use Cys to illustrate the usage.
% A general instruction to use them (here we use Cys as an example) is firstly to run

\begin{lstlisting}
$ ./min.scr cys
$ ./heat_equil_prod_param.sh cys
\end{lstlisting}

After minimization, heating, equilibration, and production thermodynamic integration,
we obtain $\partial U/\partial\theta$ values saved in files with the extension .lambda as in the folder \href{https://gitlab.com/shenlab-amber-cphmd/cphmd-tutorial/-/tree/main/parameterization/single}{single} (single site titration).
We then call the Python script to fit the A and B parameters.

\begin{lstlisting}
$ python cphmd_parm_fit.py single
\end{lstlisting}

Four files are generated: du.data, du.fit, du.png, and cphmd.parm. du.data contains the mean force data, du.fit contains the detailed fitting results, du.png is the plot of the fitting (Fig.~\ref{Fig:parm_cys}) , and cphmd.parm contains the A and B parameters that can be directly copied and pasted into the standard CpHMD parameter file.
The instructions for parameterization of different models are described in the folder \href{https://gitlab.com/shenlab-amber-cphmd/cphmd-tutorial/-/tree/main/parameterization}{parameterization} and the example results are included, as in the folders
\href{https://gitlab.com/shenlab-amber-cphmd/cphmd-tutorial/-/tree/main/parameterization/single}{single},
\href{https://gitlab.com/shenlab-amber-cphmd/cphmd-tutorial/-/tree/main/parameterization/his}{his},
and
\href{https://gitlab.com/shenlab-amber-cphmd/cphmd-tutorial/-/tree/main/parameterization/carboxyl}
{carboxyl}.
% Here is a single-column checklist that consists of multiple sub-checklists
% \begin{Checklists}

% \begin{checklist}{A list}
% \textbf{Single-column checklists are also straightforward by removing the asterisk}
% \begin{itemize}
% \item First thing let's do an item which breaks across lines to see how that looks
% \item Also remember
% \item And finally
% \end{itemize}
% \end{checklist}

% \begin{checklist}{Another list}
% \textbf{This is some further description.}
% \begin{itemize}
% \item First thing
% \item Also remember
% \item And finally
% \end{itemize}
% \end{checklist}

% \end{Checklists}


\chapter{Expected value, conditional expectation and Jensen's inequality}


\documentclass{article}

%----------------------------------------------------------------------------------------

\usepackage{listings} % Required for inserting code snippets
\usepackage{geometry}
\geometry{margin=0.7in}
\usepackage[usenames,dvipsnames]{color} % Required for specifying custom colors and referring to colors by name
\usepackage{amssymb}
\usepackage{amsmath}
\usepackage{mathtools}
\usepackage{tikz}
\usepackage{enumerate}

\definecolor{DarkGreen}{rgb}{0.0,0.4,0.0} % Comment color
\definecolor{highlight}{RGB}{255,251,204} % Code highlight color

%----------------------------------------------------------------------------------------

\begin{document}

%----------------------------------------------------------------------------------------

\section*{Problem 1}
\begin{flushleft}
\begin{enumerate}
\item $A = \{-1, 5.2,1,3.7\}$ \\
\vspace{.3cm}
\qquad \textbf{Upper bounds:} 5.2, 6\\
\vspace{.3cm}
\qquad $\forall a \in A$, $a \leq 5.2$. Thus, $5.2$ is an upper bound for $A$. \\
\vspace{.3cm}
\qquad $A$ is a finite set with 4 elements. Thus, the maximum element must also be the \emph{LUB(A)}. There cannot be \\
\qquad another least upper bound because any number $n$ less than the maximum element, $5.2$ would mean that \\
\qquad $\exists a \in A$, $a > n$, where that $a$ is $5.2$.
\vspace{.3cm}

\item $B = [2,3) = \{x \in \mathbb{R} : 2 \leq x < 3\}$\\
\vspace{.3cm}
\qquad \textbf{Upper bounds:} 3, 4\\
\vspace{.3cm}
\qquad $\forall b \in B$, $b < 3$ because $B$ approaches $3$ but does not actually contain $3$. Thus, 3 is an upper bound for $B$. \\
\vspace{.3cm}
\qquad There is no \emph{LUB(B)} $ < 3$ because the elements of the set $B$ approach $3$ infinitely close. Thus, $\forall b \in B$, \\
\qquad $b + \epsilon < 3$  meaming that there is always an element of $B$ that is more than another element but still less \\
\qquad  than $3$. Thus, $3$ must be the \emph{lub(B)}.
\vspace{.3cm}

\item $C = (-\infty, 4.2]$\\
\vspace{.3cm}
\qquad \textbf{Upper bounds:} 4.2, 5\\
\vspace{.3cm}
\qquad $\forall c \in C$, $c < 4.2$. Thus, $4.2$ is an upper bound for $C$. \\
\vspace{.3cm}
\qquad $C$ is an infinite set with a defined maximum element. Thus, the maximum element must also be the \\
\qquad \emph{LUB(C)}. There cannot be another least upper bound because any number $n$ less than the maximum \\
\qquad element, $4.2$ would  mean that $\exists c \in C$, $c > n$, where that $c$ is $4.2$.
\vspace{.3cm}

% prove this better
\item $D = \{\frac{(-1)^n}{n} : n \in \mathbb{N}\}$\\
\vspace{.3cm}
\qquad \textbf{Upper bounds:} $\frac{1}{2}$, $1$\\
\vspace{.3cm}
\qquad $\forall d \in D$, $d < \frac{1}{2}$. Thus,  $\frac{1}{2}$ is an upper bound for $D$. \\
\vspace{.3cm}
\qquad We know $\frac{1}{2} \in D$ because when $n=2$, $\frac{(-1)^{2}}{2}=\frac{1}{2}$. Let's assume there exists another least upper bound \\ \qquad $e=$\emph{LUB(D)} defined as $\frac{1}{2}-\epsilon$. By definition, $\frac{1}{2}-\epsilon$ must be greater than all elements in $D$, but we know $\frac{1}{2}$ \\
\qquad is an element and greater than $\frac{1}{2}-\epsilon$. Thus, $e$ contradicts our assumption and $\frac{1}{2}$ is the \emph{LUB(D)}.\\
\vspace{.3cm}

\item $E =\{-\frac{1}{n} : n \in \mathbb{N}\}$\\

\vspace{.3cm}
\qquad \textbf{Upper bounds:} $0$, $1$\\
\vspace{.3cm}
\qquad $\forall e \in E$, $e < 0$. Thus, $0$ is an upper bound for $E$. \\
\vspace{.3cm}
\qquad Let's choose another upper bound $f$. Assume $f < 0$. Find a $k \in \mathbb{N}$ so that $-\frac{1}{k}< |f|$. Then $\frac{1}{k} > f$. Since \\
\qquad $\frac{1}{k} \in E$, $f$ cannot be a \emph{LUB(E)}. Then, $f$ is an uppber bound and $f \geq 0$. Thus, $0$ is the \emph{LUB(E)}.
\vspace{.3cm}

\item $F = \{\sum_{k=1}^{n} \frac{1}{k} : n \in \mathbb{N}\}$\\

\vspace{.3cm}
\qquad Upper bounds: \emph{DNE}\\
\vspace{.3cm}
\qquad $F$ is an infinite set with no upper bound. Since it is not bounded above, it cannot have a \emph{LUB}.
\vspace{.3cm}

\item $G = \{cos(n) : n \in \mathbb{N}\}$\\

\vspace{.3cm}
\qquad Upper bounds: $1$, $2$\\
\vspace{.3cm}
\qquad $\forall g \in G$, $d < 1$. Thus, $1$ is an upper bound for $G$. \\
\vspace{.3cm}
\qquad The finite range of the cosine function is defined as $[-1, 1]$. The maximum element must also be the \\
\qquad \emph{LUB(G)} because $\forall g \in G$, such that $g < 1$, $g$ is not even an upper bound of $G$ and therefore cannot be a\\
\qquad \emph{LUB(G)}.
\vspace{.3cm}

\item $H = \{100n - n^2 : n \in \mathbb{N}\}$\\

\vspace{.3cm}
\qquad Upper bounds: $2500$, $2501$\\
\vspace{.3cm}
\qquad $\forall h \in H$, $h < 2500$. The $\frac{d}{dn}100n - n^2$ shows us that there is a maxima at $n=50$. When $n=50$, the \\
\qquad function takes the value $2500$. Thus, $1$ is an upper bound for $H$.\\
\vspace{.3cm}
\qquad We know $2500$ is the maximum element in the defined range of the function $100n - n^2 : n \in \mathbb{N}$.  The \\
\qquad maximum element must also be the \emph{LUB(H)} because $\forall h \in H$, such that $h < 2500$, $h$ is not even an upper \\
\qquad bound of $H$ and therefore cannot be a \emph{LUB(H)}.
\vspace{.3cm}

\end{enumerate}
\end{flushleft}

\section*{Problem 2}
\begin{center}
If $S \subset \mathbb{R}$ has a \textit{least upper bound}, then it is unique.
\end{center}

\begin{flushleft}
\textbf{Proof} \\
\vspace{.5cm}
Let $S$ be a subset of $\mathbb{R}$ and assume that $p=LUB(S)$ and therefore an upper bound for $S$ as well. Let's also assume that there exists a number $q \in \mathbb{R}$ such that $q=LUB(S)$ and therefore an upper bound for $S$ as well. We know that $p \leq q$ since $p$ is a $LUB(S)$. Likewise, we know that $q \leq p$ since $q$ is a $LUB(S)$. Because both $p \leq q$ and $q \leq p$, $b=c$ must be true. Therefore, the $LUB(S)$ must be unique.
\end{flushleft}

\section*{Problem 3}
\begin{flushleft}
Suppose that $\lambda = lub(A)$. Let $B = \{ka | \in A \}$, where $k > 0$.
\begin{enumerate}[a)]
\item Show that $k\lambda$ is an upper bound for the set $B$.\\
\vspace{.5cm}
\qquad If $\lambda$ is \emph{lub(A)}, then $\forall a \in A$, $a \leq \lambda$. If $k > 0$ and $a \leq \lambda$, we know $ka \leq k\lambda$. Thus $k\lambda$ is an upper bound of B.

\item Show that $k\lambda$ is the least upper bound for $B$. \\
\vspace{.5cm}
\qquad Let's assume there is another element $\gamma \in B$ such that $\gamma < \lambda$. Then,
\begin{center}
$ka \leq \gamma < k\lambda$\\
$a \leq \gamma / k < \lambda$\\
$\gamma / k < \lambda$\\
\end{center}
\qquad We end up with $\gamma / k$ as greater than $a \in A$ and smaller than $\lambda$. However, we defined $\lambda$ as \emph{lub(A)}. No such \\
\qquad element $\gamma$ can exist, and we end up with a contradiction. Thus, $k\lambda=$ \emph{lub(B)}.
\item What can happen if $k < 0$?\\
\vspace{.5cm}
\qquad If $k < 0$, then $a \leq \lambda$ means that $ka \geq k\lambda$. In that case, the proof above does \textbf{not} hold.

\end{enumerate}
\end{flushleft}

\section*{Problem 4}
\begin{flushleft}
Prove the following facts about real numbers, stating explicitly which field axioms/theorems you are using at each stage.
\begin{enumerate}[a)]
\item $\forall a, x \in \mathbb{R}$ if $a \neq 0$ and $ax = a$ then $x=1$.\\
\vspace{.5cm}
\qquad By A10, we know we can get $x$ alone on the left hand side of the equation $ax$ because the existence \\
\qquad of a multiplicative inverse defined by $a^{-1} = 1/a$. So, we have
\begin{center}
$a^{-1} \cdot ax = a^{-1} \cdot a $ \\
$\frac{1}{a} \cdot \frac{a}{1}x = \frac{1}{a} \cdot \frac{a}{1} $ \\
$\frac{a}{a} \cdot x = \frac{a}{a} $ \\
$1 \cdot x = 1 $ \\
$x = 1$
\end{center}
\qquad We know see that after multiplying both sides by the multiplicative inverse of $a$ becomes $\frac{a}{a}$, which reduces to \\
\qquad $1$. We are left with $x=1$, which is what we were trying to find.

\item $\forall a,b \in \mathbb{R}$ if $ab=0$ then $a=0$ or $b=0$. \\
\vspace{.5cm}
\qquad Again, by A10, we know we can utilize the existence of a multiplicative inverse to separate the variables $a$ \\
\qquad and $b$ defined as $a^{-1} = \frac{1}{a}$ and $b^{-1} = \frac{1}{b}$, respectively. \\
\begin{center}
\begin{tabular}{r r r l}
& $a^{-1} ab = 0 $ & $b^{-1} ab = 0 $ & \\
& $\frac{1}{a} \cdot ab = 0 $ & $b^{-1} ba = 0 $ & By A7\\
& $\frac{1}{a} \cdot \frac{a}{1}b = 0 $ & $\frac{1}{b} \frac{b}{1}a = 0 $ & \\
& $\frac{a}{a} \cdot b = 0 $ & $\frac{b}{b} \cdot a = 0 $ & \\
& $1 \cdot b = 0 $ & $1 \cdot a = 0 $ & \\
By A9 & $b = 0 $ & $a = 0 $ & By A9\\
\end{tabular}
\end{center}
\qquad We know see that regardless of whether we multiply $ab=0$ by the multiplicative inverse of $a$ then $b$, the \\
\qquad resulting variable is equal to $0$. \\

\item $\forall x,y \in \mathbb{R}$ if $x^2=y^2$ then $x=y$ or $x=-y$.\\
\begin{flushleft}
\qquad Let's assume that $x \neq y$ and $x \neq -y$. Then, by definition of the square of a number $a$, we get $a \cdot a = a^2$. \\

\begin{center}
\begin{tabular}{r c c r c}
In the case of $x=y$, & $x \cdot x \neq y \cdot y$ & & In the case of $x=-y$, & $x \cdot x \neq (-y)(-y)$\\
& $x^2 \neq y^2$ & & & $x^2 \neq (-1)(y)(-1)(y)$ \\
& & & & $x^2 \neq (-1)(-1)(y)(y)$ \\
& & & & $x^2 \neq (y)(y)$ \\
& & & & $x^2 \neq y \cdot y$ \\
& &  & & $x^2 \neq y^2$\\
\end{tabular}
\end{center}
\qquad According to our assumption, we see that in either case, we get $x^2 \neq y^2$. However, that contradicts the \\
\qquad original hypothesis. Thus, $x = y$ or $x = -y$.\\

\end{flushleft}
\end{enumerate}
\end{flushleft}

%----------------------------------------------------------------------------------------

\end{document}


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

\begin{document}

\title{HW\#4 || Graph Clustering Algorithms}
\author{Saket Choudhary}
\maketitle

\section*{Markov Clustering(MCL)}

Markov clustering makes use of stochastic flows in a graph. The underlying idea is
that a random walk on a dense cluster is likely to stay on the vertices of this cluster before
jumping to other cluster. This property is made use by simulating a stochastic flow on the graph
such that the flow be inflated wherever the current is strong and downweighted otherwise. This can
thus be formulated as a Markov graph. The flows are modelled by calculating successive powers of the matrix.

\section*{Restricted Neighborhood Search(RNSC)}
RNS clustering tries to minimises a cost function that captures the weight of
inter and intra cluster edges. With a random initial value, RNSC iteratively assigns
a node to other cluster if that leads to a local minima. Termination can be defined based on number of iterations
or convergence of the cost function.

\section*{Molecular Complex Detection(MCODE)}
Molecular complex detection assigns a weight to each vertex that is proportional
to the number of neighbors. Starting from the heaviest vertex it iteratively moves out
assigning each vertex to the cluster if it is above a certain threshold.
\section*{Comparison}
All thress algorithms are parametric and hence the quality of clustering will depend on the choice of appropriate parameters.

\textbf{Robustness}: MCL and RNSC are more robust to noise and missing information in the data, while they are also more robust towards the choice of parameters. Hence in case of missing data  MCL or RNSC might be a better choice over MCODE.

\textbf{Heuristic} RNSC and MCODE are heuristic and hence the convergence depends on the initial set of clusters/vertices chosen

\section*{References}
Brohee, Sylvain, and Jacques Van Helden. "Evaluation of clustering algorithms for protein-protein interaction networks." BMC bioinformatics 7.1 (2006): 488.
\end{document}


\section{Tests and Results}

\subsection{Results Exact Method}
	The result igureof Exact method in table\ref{tab:ExactMethodResults} comes from the execution of eight time the program in order to have a better estimate for the time in seconds.

	\begin{table}[h]
		\centering
		\begin{tabular}{lrrr}
			\toprule
			\textbf{Instance} & \textbf{Obj. Value} & \textbf{User Time (s)} & \textbf{Avg. CPU time (s)} \\
			\midrule
			\verb|tsp12| & 66.40 & 0.085 & 0.240 \\
			\verb|tsp60| & 629.80 & 11.240 & 36.129 \\
			\verb|rnd60| & 311.97 & 8.022 & 27.833 \\
			\verb|fb60|	& 240.47 & 24.498 & 61.198 \\
			\verb|rnd80| & 348.11 & 17.765 & 54.858 \\
			\verb|fb80| & 219.37 & 95.216 & 261.729 \\
			\verb|rnd100| & 370.09 & 30.247 & 85.942 \\
			\verb|rnd100_2| & 457.54 & 57.178 & 174.448 \\
			\verb|fb100| & 276.55 & 106.757 & 286.079 \\
			\bottomrule
		\end{tabular}
		\caption{\label{tab:ExactMethodResults} Results Exact method}
	\end{table}

	There isn't much to say about the exact method results. From the results (table~\ref{tab:ExactMethodResults}) we can see as expected that there is a trend where the increase of the number of nodes increase exponentially the CPU time (figure~\ref{fig:em-results-time}). This is not always the case, in fact the time depends a lot by the instance and the type of the instance, \verb|fb| require always more time than the other instances. The CPU time of \verb|rnd100|, \verb|rnd100_2| and \verb|fb100| show this (look at table \ref{tab:ExactMethodResults}).

	\begin{figure} [hb]
		\centering
		\includegraphics[width=\linewidth]{img/EM-results-time}
		\caption{Exact Method average CPU time for each instance}
		\label{fig:em-results-time}
	\end{figure}

\newpage
\subsection{Results Local Search}
\label{subsec:results-ls}
	The Local Search is tremendously fast but at a cost of found the optimal solution only in some instance and in average it performs poorly in comparison with other methods. In this test the User time is ignore as it is equal to CPU time, no parallel computation was implemented into meta heuristics algorithms.

	It's interesting to note the average result of Local Search. I run the LS Best Improvement (BI) and LS First Improvement (FI) with 8 random initial solution for each instance. The average results show that FI is almost always the better choice at a cost of a bit more time, that is the time needed to explore more solutions.

	A \textbf{good strategy} for use Local Search is to start from a lot of different initial solution, in the table~\ref{tab:LS-BestStrategyResult} I summarized the results of this strategy, every local search is started with eight different random solution and the \textbf{best value} found is selected. The \textbf{CPU time} corresponds to the sum of the time of all tabu searches ran for each instance.

	An interesting fact that I observed is illustrated in the figure~\ref{fig:ls-convergence}, where it's shown that with the \verb|fb| instances we have a faster convergence than in the others.

	\vspace{2cm}

	\begin{figure}[hb]
		\centering
		\includegraphics[width=\linewidth]{img/LS-time}
		\caption{Local Search time for each instance for each feature (BI or FI)}
		\label{fig:ls-time}
	\end{figure}

\newpage

	\begin{figure}[H]
		\centering

		\includegraphics[width=\linewidth]{img/LS-convergence}

		\vspace{1cm}

		\includegraphics[width=\linewidth]{img/LS-convergence60}

		\caption{The faster convergence of fb instances respect to the others.}
		\label{fig:ls-convergence}
	\end{figure}

\newpage

	\begin{table}[H]

		\begin{tabular}{llrrr}
			\toprule
			\textbf{Instance} & \textbf{Feature} & \textbf{Avg Value} & \textbf{Avg Time (s)} & \textbf{Avg Quality} (\%) \\
			\midrule
			\verb|tsp12| 	& Best Improv. & 66.850 & 4.125e-05 & 98.3 \\
			& First Improv. & 67.325 & 7.3875e-05 & 98.6 \\
			\midrule
			\verb|tsp60| 	& Best Improv. & 666.650 & 0.00071163 & 94.5 \\
			& First Improv. & 657.362 & 0.00101625 & 95.8 \\
			\midrule
			\verb|rnd60| 	& Best Improv. & 332.826 & 0.00073738 & 93.7 \\
							& First Improv. & 329.934 & 0.00096238 & 94.6 \\
			\midrule
			\verb|fb60|		& Best Improv. & 255.999 & 0.00056363 & 93.9 \\
							& First Improv. & 256.786 & 0.00067400 & 93.6 \\
			\midrule
			\verb|rnd80| 	& Best Improv. & 374.400 & 0.00129013 & 93.0 \\
							& First Improv. & 371.325 & 0.00198488 & 93.7 \\
			\midrule
			\verb|fb80|		& Best Improv. & 228.525 & 0.00135700 & 95.9 \\
							& First Improv. & 233.497 & 0.00151600 &  93.9 \\
			\midrule
			\verb|rnd100| 	& Best Improv. & 406.499 & 0.00266875 & 91.0 \\
							& First Improv. & 391.406 & 0.00358875 & 94.6 \\
			\midrule
			\verb|rnd100_2| & Best Improv. & 495.690 & 0.00230150 & 92.3 \\
							& First Improv. & 492.135 & 0.00302388 & 93.0 \\
			\midrule
			\verb|fb100| & Best Improv. & 296.774 & 0.00242475 & 93.2 \\
						& First Improv. & 291.699 & 0.00254362 & 95.1 \\
			\bottomrule
		\end{tabular}
		\caption{\label{tab:AvgResultLS}Average results of all Local Search BI and FI executed}
	\end{table}

	\begin{table}[H]
		\centering
		\begin{tabular}{llrrr}
			\toprule
			\textbf{Instance} & \textbf{Feature} & \textbf{Best Value} & \textbf{Tot Time (s)} & \textbf{Quality (\%)} \\
			\midrule
			\verb|tsp12| & Best Improv. & 66.4 & 0.000415 & 100 \\
							& First Improv. & 66.4 & 0.000610 & 100 \\
			\midrule
			\verb|tsp60| 	& Best Improv. & 634.6 & 0.009326 & 99.2 \\
							& First Improv. & 638.6 & 0.009972 & 98.6 \\
			\midrule
			\verb|fb60|		& Best Improv. & 243.74 & 0.004509 & 98.6 \\
							& First Improv. & 243.47 & 0.005392 & 98.8 \\
			\midrule
			\verb|rnd60| 	& Best Improv. & 319.35 & 0.009223 & 97.7 \\
							& First Improv. & 314.53 & 0.009503 & 99.2 \\
			\midrule
			\verb|rnd80| 	& Best Improv. & 351.69 & 0.012120 & 99.0 \\
							& First Improv. & 351.05 & 0.018155 & 99.1 \\
			\midrule
			\verb|fb80| 	& Best Improv. & 223.9 & 0.010856 & 97.9 \\
							& First Improv. & 224.35 & 0.012128 & 97.7 \\
			\midrule
			\verb|rnd100| 	& Best Improv. & 387.45 & 0.028099 & 95.5 \\
							& First Improv. & 372.25 & 0.033198 & 99.4 \\
			\midrule
			\verb|rnd100_2| & Best Improv. & 476.34 & 0.023825 & 96.1 \\
							& First Improv. & 483.14 & 0.027648 & 94.7 \\
			\midrule
			\verb|fb100| & Best Improv. & 280.37 & 0.019398 & 98.6 \\
						& First Improv. & 282.99 & 0.020349 & 97.7 \\
			\bottomrule
		\end{tabular}
		\caption{\label{tab:LS-BestStrategyResult} Results of Local Search with Best Improvement and First Improvement, the result selected are only the best found from eight random initial solution}
	\end{table}

\newpage
\subsection{Results Tabu Search}

	\subsubsection{Calibration}
	\label{subsec:calibration}
	For calibration of the Tabu Search algorithm I look only to the tabu list length parameter. Hence I evaluate the test by the result obtained in \textbf{30 seconds} (CPU time),  every calibration test was be done with 30 seconds time-out. Note that if we increase the size of tabu list we need more time for check if one Move is a tabu.

	I tested the following instances (\verb|.dat|):
	\begin{itemize}
		\item \verb|tsp60|
		\item \verb|rnd80|
		\item \verb|fb80|
		\item \verb|rnd100|
	\end{itemize}

	The results of calibration phase are summarized in the charts \ref{fig:ts-calibration-rnd80} and \ref{fig:ts-calibration-rnd100}. In the Y axe we have the average of Objective value, in the X axe we have the tabu length.

	From these charts we can see that:
	\begin{itemize}
		\item With a large tabu length the aspiration criteria reduce the average obj. values;
		\item Different instances produce different result with the same tabu length;
		\item Long tabu length is better for instances with more nodes, this is the case for \verb|fb80| and \verb|rnd100|. For \verb|rnd80| instead we have better result only if there are aspiration criteria enabled;
		\item Long tabu length makes the average result worse in small instance: \verb|tsp60|;
		\item There are only little differences between Best Improvement and First Improvement.
	\end{itemize}

	From these consideration I chose to test tabu search with three type of length:
	\begin{itemize}
		\item Small: 100;
		\item Medium: 180 (the best choice from calibration result);
		\item Large: 240;
	\end{itemize}
	Since Aspiration Criteria sometimes improve the solutions \ref{fig:ts-calibration-rnd80} and there are not marked differences between Best improvement and First Improvement I will test only tabu search with \textbf{Best Improvement} and \text{Apiration Criteria}

	\begin{figure}[p]
		\centering
		\includegraphics[width=\linewidth]{img/TS-calibration-tsp60}
		%\caption{}
		%\label{fig:ts-calibration-tsp60}
	%\end{figure}

	\vspace{2cm}

	%\begin{figure}
		%\centering
		\includegraphics[width=\linewidth]{img/TS-calibration-rnd80}
		\caption{Comparison between the different Tabu length for tsp60 and rnd80 instances.}
		\label{fig:ts-calibration-rnd80}
	\end{figure}

	\begin{figure}[p]
		\centering
		\includegraphics[width=\linewidth]{img/TS-calibration-fb80}
		%\caption{}
		%\label{fig:ts-calibration-fb80}
	%\end{figure}

	\vspace{2cm}

	%\begin{figure}
		%\centering
		\includegraphics[width=\linewidth]{img/TS-calibration-rnd100}
		\caption{Comparison between the different Tabu length for fb80 and rnd100 instances.}
		\label{fig:ts-calibration-rnd100}
	\end{figure}

%	\begin{figure}[bh]
%		\centering
%		\includegraphics[width=\linewidth]{img/TS-calibration-rnd100_2}
%		\caption{Comparison between the different Tabu settings for rnd100 instance.}
%		\label{fig:ts-calibration-rnd1002}
%	\end{figure}

\newpage

	\subsubsection{Tests}
		I tested the Tabu Search implementation with three different strategy.

		\paragraph{Strategy 1} The Tabu Search is set as explained in the calibration phase~\ref{subsec:calibration}. The CPU time set is 30 seconds. We can see that in the case of small instance (60 nodes) the tabu with 100 of length found a better solution than the tabu with length of 180. Interesting also in the \verb|rnd100_2| instance with length of 100 we get a better solution. If we look at the optimal results \ref{tab:ExactMethodResults} we see that these better solutions are de facto the optimal solutions.

		\paragraph{Strategy 2} In this strategy I try to do diversification, I start 4 Tabu search with 3 different initial random solutions, the total time is 30 seconds, hence 10 seconds for each tabu search executed. From the result we can see that this strategy in some cases can improve the result found in the previously strategy. Accordingly to that is better to call multiple Tabu Search with different initial solution instead of one, in the same amount of time.

		\paragraph{Strategy 3} In the third strategy instead I only increase the number of CPU time from 30 to 60 second in order to see if Tabu search improve results that are not optimal. In table~\ref{tab:ts-results} we can see that this is not the case, for all the instances increasing  time of 30 seconds did not improve the best value found with \textbf{Strategy 1}.

		\paragraph*{} From the table \ref{tab:ts-results} we can see that the \textbf{Strategy 2} is the best, in the table \ref{tab:ts-result-q} we see that the Tabu Search found the optimum almost in all instances. From these results I think that the best ways to increase the probability to find the optimum are:
		\begin{itemize}
			\item execute more than one Tabu Search with different random initial solutions;
			\item execute Tabu Search with different tabu length.
		\end{itemize}

		\vspace{1cm}

		\begin{table}[h]
			\centering
			\begin{tabular}{l r r r}
				\toprule
				\textbf{Instance \textbackslash~Length} & \textbf{100}    & \textbf{180}    & \textbf{240}    \\
				\midrule
				\verb|tsp12|                              & 66.40   & 66.40   & 66.40   \\
				\verb|tsp60|                              & 629.80  & 631.40  & 630.80  \\
				\verb|rnd60|                              & 311.97 & 312.09 & 312.09 \\
				\verb|fb60|                               & 247.95 & 247.95 & 247.95 \\
				\verb|rnd80|                              & 348.11 & 348.23 & 348.11 \\
				\verb|fb80|                               & 222.72 & 222.70  & 222.70  \\
				\verb|rnd100|                             & 376.20  & 370.09 & 370.09 \\
				\verb|rnd100_2|                           & 457.54 & 459.30  & 460.24 \\
				\verb|fb100|                              & 288.14 & 288.14 & 279.74 \\
				\bottomrule
			\end{tabular}
			\caption{Tabu Search BI with AC results with three different type of tabu length}
			\label{tab:ts-result}
		\end{table}

	\begin{table}[]
		\centering
		\begin{tabular}{lrrr}
			\toprule
		\textbf{Instance} & \textbf{Strategy 1} & \textbf{Strategy 2} & \textbf{Strategy 3} \\
			\toprule
		\verb|tsp12|     & 66.40               & 66.40     & 66.40     \\
		\verb|tsp60|     & 631.40              & 630.8     & 631.40      \\
		\verb|rnd60|     & 312.09              & 312.09     & 312.09    \\
		\verb|fb60|      & 247.95              & 240.47     & 247.95    \\
		\verb|rnd80|     & 348.23              & 348.11     & 348.23    \\
		\verb|fb80|      & 222.70              & 222.70     & 222.70    \\
		\verb|rnd100|    & 370.09              & 370.09     & 370.09   \\
		\verb|rnd100_2|  & 459.30              & 459.30    & 459.30     \\
		\verb|fb100|     & 288.14              & 278.56     & 288.14    \\
			\bottomrule
		\end{tabular}
		\caption{Results of Tabu Search BI AC with the three different strategies}
		\label{tab:ts-results}
	\end{table}

	\begin{table}[]
		\centering
		\begin{tabular}{lrr}
			\toprule
			\textbf{Instance} & \textbf{Strategy 2}& \textbf{Quality (\%)}\\
			\toprule
			\verb|tsp12|           & 66.40      & 100	  \\
			\verb|tsp60|           & 630.8     & 99.8    \\
			\verb|rnd60|           & 312.09     & 99.9    \\
			\verb|fb60|            & 240.47     & 100     \\
			\verb|rnd80|           & 348.11      & 100     \\
			\verb|fb80|            & 222.70      & 98.5    \\
			\verb|rnd100|          & 370.09      & 100     \\
			\verb|rnd100_2|        & 459.30      & 99.6    \\
			\verb|fb100|           & 278.56      & 99.2        \\
			\bottomrule
		\end{tabular}
		\caption{Quality of the result for Tabu Search with multiple start strategy}
		\label{tab:ts-result-q}
	\end{table}


% Chapter X

\chapter{Figaro's representation} % Chapter title

\label{Figaro's representation} % For referencing the chapter elsewhere, use

This section describes the basic building blocks of Figaro models. We present the basic definitions of different kinds of model components. In the following section, we will show how to use these components to create a rich variety of models.

\section{Elements}
All data structures that are part of a Figaro model are \emph{elements}. Elements can be combined in various ways to produce more complex elements. The simplest elements are \emph{atomic} elements that do not depend on other elements. An example of an atomic element is

\begin{flushleft}
\marginpar{Figaro classes are capitalized, while Scala reserved words are not}
\texttt{Constant(6)}
\end{flushleft}

This defines the probabilistic model that produces the integer 6 with probability
1. Another atomic element is
\begin{flushleft}
\texttt{Constant("Hello")}
\end{flushleft}

which produces the string "Hello" with probability 1. These two examples illustrate that every Figaro element has a \emph{value type}, which in the first case is \texttt{Int} and in the second case \texttt{String}. The value type is the type of values produced by the probabilistic model defined by the element.

\marginpar{Scala uses type inference, so the value type of the parameter can often be omitted at class creation (the compiler will determine the type)}

Scala is an object-oriented language, so all Figaro elements are instances of an \texttt{Element} class. The \texttt{Element} class is parameterized by its value type. In Scala's notation, the first element is an instance of \texttt{Element[Int]} while the second is an instance of \texttt{Element\-[String]}.

A constant is a particular type of element that is an instance of the \texttt{Constant}
class, which is a subclass of \texttt{Element}. So, more specifically, the first element Scala uses type inference, so the value type of the parameter can often be omitted at class creation (the compiler will determine the type) above is an instance of \texttt{Constant[Int]}. Figaro's representation is defined by a class hierarchy under
\texttt{Element}.

Every Figaro \texttt{Element[U]} has a \emph{value}, which represents the current value of the element and is of type \texttt{U}. For \texttt{Constant} elements, the value of the element never changes. However, for stochastic elements, the value of the element may change depending on the usage of the model, as explained in the next section.

\section{Atomic elements}

An \emph{atomic} element is one that does not depend on any other elements. Constants are unusual atomic elements in that they are not random. All the other built-in atomic classes contain some aspect of randomness. We illustrate some of these classes by examples.

\begin{itemize}
\item \texttt{Flip(0.7)} is an \texttt{Element[Boolean]} that represents the probabilistic model that produces true with probability 0.7 and false with probability 0.3.
\item \texttt{Select(0.2 -> 1, 0.3 -> 2, 0.5 -> 3)} is an \texttt{Element[Int]} that represents the probabilistic model that produces 1 with probability 0.2, 2 with probability 0.3, and 3 with probability 0.5. \texttt{Select} can select between elements of any type, so we may also have
\texttt{Select(0.4 -> "a", 0.6 -> "b")}, which is an \texttt{Element\-[String]}.
\item The continuous \texttt{Uniform(0.0, 2.0)} is an \texttt{Element[Double]} that represents the continuous uniform probability distribution between 0 and 2.
\end{itemize}

Elements also contain a method for generating a new value for the element. This is accomplished by called the \texttt{generate()} method of an element. Generating a new value of an element is a two step process. First, the \texttt{generate()} method generates a new \emph{randomness} for the element. Then, the value of an atomic element is \emph{deterministically} produced as a function of the randomness of the element. For example, consider the \texttt{Flip(0.7)} shown above. To determine the value of this \texttt{Flip}, a number between 0 and 1 is uniformly chosen as the randomness of the element, and if the value is less than 0.7, we assign the \texttt{Flip} a value of \texttt{true}, and \texttt{false} otherwise.

While \texttt{Flip} and \texttt{Select} are in the \texttt{language} package that was imported earlier, \texttt{Uniform} is in the \texttt{library.atomic.continuous} package that needs to be imported using

\begin{flushleft}
\marginpar{The \_ is the Scala version of Java's * for imports}
\texttt{import com.cra.figaro.library.atomic.continuous.\_}
\end{flushleft}

Other built-in continuous atomic classes include \texttt{Normal, Exponent\-ial, Gamma, Beta}, and \texttt{Dirichlet}, also found in the \texttt{library.atomic.\-continuous package}, while discrete elements include discrete \texttt{Uniform, Geometric, Binomial}, and \texttt{Poisson}, to be found in the \texttt{library.atomic.\-discrete package}.

\section{Compound elements}

In \texttt{Flip(0.7)}, the argument to \texttt{Flip} is a \texttt{Double}. There is another version of \texttt{Flip} in which the argument is an \texttt{Element[Double]}. For example, we might have

\begin{flushleft}
\texttt{Flip(Uniform(0.0, 1.0)) }
\end{flushleft}

which represents the probabilistic model that produces \texttt{true} with a probability that is uniformly distributed between 0 and 1. This is a \emph{compound} element that is built from another element. Most of the atomic elements described in the previous subsection have compound versions.

Another example of a compound element is a conditional. The element

\begin{flushleft}
\marginpar{Note \texttt{If} is a Figaro class, not the Scala \texttt{if} reserved word }
\texttt{If(Flip(0.7), Constant(1), Select(0.4 -> 2, 0.6 -> 3))}
\end{flushleft}

represents the \texttt{Element[Int]} in which with probability 0.7, \texttt{Constant\-(1)} is chosen, producing 1 with probability 1, while with probability 0.3, \texttt{Select(0.4
-> 2, 0.6 -> 3)} is chosen, producing 2 with probability 0.4 and 3 with probability 0.6. Overall, 1 is produced with probability 0.7 * 1 = 0.7, 2 with probability 0.3 * 0.4 = 0.12, and 3 with probability 0.3 * 0.6 = 0.18. The first argument to \texttt{If} must be an \texttt{Element[Boolean]}, while the other two arguments must have the same value type, which also becomes the value type of the \texttt{If}. \texttt{If} can be found in the \texttt{library.compound package}. Similar to the atomic elements, the value of a compound element can be generated by calling the \texttt{generate()} method of the element. In this case, however, the value of an element is a deterministic function of its randomness and the current value of the element's parents.

\section{Chain}

Figaro provides a useful building block for building compound elements, called \emph{chain}. Intuitively, a chain takes a probability distribution over a "parent" element and a conditional probability distribution over a "child" element given the parent to produce a distribution over the child.

A \texttt{Chain} has two type parameters, \texttt{T} and \texttt{U}, where \texttt{T} is the value type of the parent element and \texttt{U} is the value type of the child element. A \texttt{Chain[T,U]} takes two arguments: (1) an \texttt{Element[T]}, representing the parent element, and (2) a function from a value of type \texttt{T} to an \texttt{Element[U]}, representing the conditional distribution. Scala's notation for this type of function is \texttt{T => Element[U]}. For each possible value of the parent element, this function specifies an element defining the distribution over the child. The \texttt{Chain} itself represents the probability distribution over the child that results from this chaining. Thinking in terms of a generative process, a \texttt{Chain} represents the probabilistic
\marginpar{Scala notation for the type of a function is: \texttt{inType => outType}}
model in which first a value of type \texttt{T} is produced from the parent argument, then the function in the second argument is applied to this value to generate a particular \texttt{Element[U]}, and finally a particular value of type \texttt{U} is randomly produced from the generated \texttt{Element[U]}. Therefore, a \texttt{Chain[T,U]} is an \texttt{Element[U]}.

For example,
\begin{flushleft}
\texttt{Chain(Flip(0.7), (b: Boolean) =>
\newline \tab if (b) Constant(1); else Select(0.4 -> 2, 0.6 -> 3))}
\end{flushleft}

represents exactly the same probabilistic model as

\begin{flushleft}
\texttt{If(Flip(0.7), Constant(1), Select(0.4 -> 2, 0.6 -> 3))}
\end{flushleft}

Let's understand this example from the inside out. First,

\begin{flushleft}
\texttt{if (b) Constant(1); else Select(0.4 -> 2, 0.6 -> 3)}
\end{flushleft}

is a Scala expression. \texttt{b} is a Boolean variable. If \texttt{b} is true, the expression produces the element \texttt{Constant(1)}, otherwise it produces the element \texttt{Select(0.4 -> 2, 0.6 -> 3)}. Note that this is a Scala expression, not Figaro's conditional data structure (all Figaro classes are capitalized). Now,

\begin{flushleft}
\texttt{(b: Boolean) =>
\marginpar{Anonymous functions in Scala are created by defining an argument list and the body of the function. The return type is inferred by the compiler}
\newline \tab if (b) Constant(1); else Select(0.4 -> 2, 0.6 -> 3)}
\end{flushleft}

is Scala's way of defining an anonymous function from an argument named \texttt{b} of type \texttt{Boolean} to a result defined by this \texttt{if} expression. This function is the second argument to the chain. The first argument is the element \texttt{Flip(0.7)}. The chain represents the probabilistic model in which first a \texttt{Boolean} is produced, where true is produced with probability 0.7, then the function is applied to obtain either \texttt{Constant(1)} or \texttt{Select(0.4 -> 2, 0.6 -> 3)}, and finally the resulting element is used to produce an integer.

This is exactly the same model as that represented by the conditional element in the previous subsection. It is easy to see that any conditional can be represented by a chain in a similar way. Chaining is in fact an extremely powerful concept and we will see a number of examples of it in this tutorial. It is sufficient to represent all compound elements. All the compound elements in the previous section can be
represented using a chain, and many of them are actually implemented that way. Note that there is a version of \texttt{Chain} that utilizes two parents and requires a function from a tuple of the parent types to the output type. If more parents are required for a \texttt{Chain}, multiple \texttt{Chains} can be nested together.

\section{Apply and Inject}

Another useful tool for building elements is \texttt{Apply.Apply} serves to lift Scala functions that operate on values to Figaro elements. For example,

\begin{flushleft}
\marginpar{Figaro \texttt{Apply} is a class, different than the Scala apply which is a method defined on many classes}
\texttt{(i: Int) => i + 5}
\end{flushleft}

is the Scala function that adds 5 to its integer argument.

\begin{flushleft}
\texttt{Apply(Select(0.2 -> 1, 0.8 -> 2), (i: Int) => i + 5)}
\end{flushleft}

is the Figaro element representing the probabilistic model in which first either 1 or 2 is produced with the corresponding probability, and then 5 is added to the result. In the resulting probabilistic model, 6 is produced with probability 0.2 and 7 is produced with probability 0.8. There are versions of \texttt{Apply} defined for functions of up to 5 arguments.

\marginpar{Sequences in Scala are similar to Java. \texttt{Seq} is the superclass in Scala for many types of data structures, such as \texttt{List}.}

Often, one needs to apply a function to a whole sequence of arguments. \texttt{Inject} is provided for this. \texttt{Inject} takes a sequence of elements with value type \texttt{T} and produces an element whose value type is sequences of values of type \texttt{T}. In Scala notation, \texttt{Inject} takes a variable number of arguments of type \texttt{Element[T]} and produces an \texttt{Element[Seq[T]]}. The name "inject" refers to the fact that the sequence of arguments is injected inside the element.

In Scala, a variable number of arguments are simply listed as arguments. For example, suppose we have the elements \texttt{Constant(1)} and  \texttt{Select(0.2 -> 2, 0.8 -> 3)}. Then

\begin{flushleft}
\marginpar{The notation: \_* will turn any Scala sequence into a variable argument list. The function receiving the variable argument list will have a * on the last argument}
\texttt{Inject(Constant(1), Select(0.2 -> 2, 0.8 -> 3))}
\end{flushleft}

represents the probabilistic model that produces the sequence (1, 2) with probability
0.2 and (1, 3) with probability 0.8.

If you already have a sequence, it can be turned into a variable argument list using the notation :\_*. For example, you can use

\begin{flushleft}
\texttt{Inject(List(Constant(1), Select(0.2 -> 2, 0.8 -> 3)):\_*)}
\end{flushleft}

which has the same effect as listing the individual entries of the \texttt{List} in the argument list.

Using \texttt{Inject} and \texttt{Apply}, we can apply a function to a sequence of arguments. First, consider the Scala function

\begin{flushleft}
\marginpar{Calling map on a Scala sequence will apply the same function to every value in the sequence and return a new sequence. It uses anonymous function semantics}
\texttt{(xs: Seq[Int]) => xs.map((x: Int) => x + 5)}
\end{flushleft}

\texttt{map} is a Scala method that can be applied to sequences. It takes as argument a function on elements of the sequence, applies the function to every member of the sequence, and returns the resulting sequence. So, the above function takes a sequence of integers and adds 5 to every element in the sequence. Now we can write

\begin{flushleft}
\texttt{Apply(Inject(Constant(1), Select(0.2 -> 2, 0.8 -> 3)),
\newline \tab (xs: Seq[Int]) => xs.map((x: Int) => x + 5))}
\end{flushleft}

This represents the probabilistic model that produces the sequence (6, 7) with probability 0.2 and (6, 8)with probability 0.8.

Finally, there are a variety of operators and functions that are defined using \texttt{Apply}. For example
\begin{itemize}
\item \textasciicircum \textasciicircum \ creates tuples. For example, \textasciicircum \textasciicircum(x, y) where \texttt{x} and \texttt{y} are elements, creates an element of pairs. \textasciicircum \textasciicircum \ is defined for up to five arguments. The arguments can have different value types.
\item If \texttt{x} is an element whose value type is a \texttt{tuple}, x.\_1 is an element that corresponds to extracting the first component of \texttt{x}. Similarly for \_2, \_3, \_4, and \_5.
\item \texttt{x} === \texttt{y}, where \texttt{x} and \texttt{y} have the same value type, is the element that produces true whenever they are equal. Similarly for !=.
\item A standard set of Boolean and arithmetic operators is provided.
\end{itemize}


\documentclass[9pt,a4paper,twocolumn,oneside]{article}
\usepackage{amsmath}
\topmargin=0pt
\headheight=0pt
\headsep=0pt
\textheight=760pt
\footskip=0pt
\voffset=-50pt
\textwidth=540pt
\marginparsep=0pt
\marginparwidth=0pt
\marginparpush=0pt
\oddsidemargin=0pt
\evensidemargin=0pt
\hoffset=-30pt

% Begin here
\begin{document}
\scriptsize
\section{Structures}
\subsection{Big Integer}
\begin{verbatim}
#include<cstdio>
#define lld "lld" //change this into "I64d" if using windows.
const int Size=100;
const long long D=1000000000ll;
char __tmp[(Size+5)*9];
class bigint
{
    void fix(){
        s[n]=0;
        for(int i=0;i<n;i++)
            s[i+1]+=s[i]/D,s[i]%=D;
        if(s[n])n++;
        s[n]=0;
    }
public:
    int n;
    long long s[Size];
    bigint(const char a[]){
        int i;
        for(i=0;a[i];i++);
        for(n=0;(i-=9)>=0;n++)
            sscanf(a+i,"%9"lld,s+n);
        sprintf(__tmp,"%%%d"lld,9+i);
        if(i+9>0)sscanf(a,__tmp,s+n++);
        s[n]=0;
    }
    bigint(const long long &a){s[1]=a/D,s[0]=a%D,s[2]=0,n=1+!!s[1];}
    bigint(const int &a){*this=0ll+a;}
    bigint(){*this=0;}
    const char *tostr()const{
        int i,j;
        char *t=__tmp;
        sprintf(t,"%lld",s[n-1]);
        for(i=0;t[i];i++);
        for(j=n-2;j>=0;j--,i+=9)
            sprintf(t+i,"%09lld",s[j]);
        return t;
    }
    bigint& operator+=(const bigint &t)
    {
        for(int i=n;i<=t.n;i++)s[i]=0;
        if(n<t.n)n=t.n;
        for(int i=0;i<t.n;i++)
            s[i]+=t.s[i];
        fix();
        return *this;
    }
    bigint& operator*=(const bigint &t)
    {
        bigint tmp=*this;
        const long long *a=tmp.s,*b=t.s;
        if(b==s)b=a;
        n+=t.n;
        for(int i=0;i<=n;i++)s[i]=0;
        for(int i=0;i<tmp.n;i++)
            for(int j=0;j<t.n;j++)
            {
                s[i+j]+=a[i]*b[j];
                s[i+j+1]+=s[i+j]/D,s[i+j]%=D;
            }
        while(n>1 && !s[n-1])n--;
        return *this;
    }
/*  inline void operator+=(const int &x)
    {
        s[0]+=x;
        fix();
    }
    inline void operator*=(const int &x)
    {
        for(int i=0;i<n;i++)
            s[i]*=x;
        fix();
    }*/
};
\end{verbatim}
\subsection{Fibonacci Heap}
\begin{verbatim}
struct node
{
    int d,v,dg,mark;
    node *left,*right,*parent,*child;
    bool operator<(node a){return d<a.d;}
    void move(node *ptr)
    {
        left->right=right,right->left=left;
        left=ptr,right=ptr->right;
        left->right=this,right->left=this;
    }
    void link(node *p)
    {
        parent=p,p->dg++;
        if(!p->child)p->child=this;
        move(p->child);
    }
    void cut(node *&min)
    {
        if(!parent)return;
        parent->child=right;
        if(parent->child==this)parent->child=0;
        move(min);
        if(parent->mark)parent->cut(min);
        else parent->mark=1,parent->dg--;
        parent=0;
        if(*this<*min)min=this;
    }
    void decrease(int nd,node *&min)
    {
        d=nd;
        if(parent){if(*this<*parent)cut(min);}
        else if(*this<*min)min=this;
    }
};
class Fheap
{
    node *list[30];
    void bond()
    {
        int i,d;
        node *now,*next;
        for(i=0;i<30;i++)list[i]=0;
        min->parent=0,next=min->right;
        do{
            now=next,now->parent=0;
            next=now->right;
            d=now->dg;
            while(list[d])
            {
                if(*now<*list[d])list[d]->link(now);
                else now->link(list[d]),now=list[d];
                list[d++]=0;
            }
            list[d]=now;
        }while(now!=min && !min->parent);
        for(i=0;i<30;i++)
            if(list[i] && *list[i]<*min)
                min=list[i];
        while(min->parent)min=min->parent;
    }
public:
    int n;node *min;
    Fheap(){min=0,n=0;}
    node *insert(int d,int v)
    {
        node *ptr=new node;
        *ptr=(node){d,v,0,0,ptr,ptr,0,0};
        if(n++,min)ptr->move(min);
        else min=ptr;
        if(*ptr<*min)min=ptr;
        return ptr;
    }
    node extractmin()
    {
        node tmp=*min,*ptr=min;
        if(min->child)
        {
            min->right->left=min->child;
            min->child->right->left=min;
            ptr=min->right,min->right=min->child->right,
            min->child->right=ptr;
            min->child=0;
        }
        ptr=min,min=min->right;
        ptr->move(ptr);
        if(--n)bond();
        else min=0;
        delete ptr;
        return tmp;
    }
};

\end{verbatim}
\section{Graph}
\subsection{Minimum Spaning tree and Disjoint sets}
\begin{verbatim}
#include<algorithm>
using namespace std;
const int V=1000;
int n,m,p[V],d[V],c[V][V];
int find(int v){
    if(p[v]==v)return v;
    return p[v]=find(p[v]);
}
void uni(int a,int b){
    a=find(a),b=find(b);
    if(d[a]<d[b])p[a]=b;
    else p[b]=a;
    if(d[a]==d[b])d[a]++;
}
void init(int n){
    while(n--)p[n]=n,d[n]=0;
}
struct pt{
    int x,y;
    int operator+(pt a){return (x-a.x)*(x-a.x)+(y-a.y)*(y-a.y);}
}pos[V];
struct ed{
    int s,t,c;
    bool operator<(ed x)const{return c<x.c;}
}s[V*V];
int kuskal(){
    std::sort(s,s+m);
    init(n);
    int i,sum;
    for(i=0;i<m;i++){
        if(find(s[i].s)==find(s[i].t))continue;
        uni(s[i].s,s[i].t);
        sum+=s[i].c;
    }
    return sum;
}
int prim(){
    const int inf=2147483647;
    int i,j,sum=0;
    for(i=0;i<n;i++)
        if(c[0][i]<inf)
            d[i]=c[0][i],p[i]=0;
        else d[i]=inf,p[i]=i;
    p[0]=-1;
    while(1){
        for(i=0;i<n;i++)
            if(d[i]>=0 && d[i]<inf)break;
        if(i>=n)break;
        for(j=i+1;j<n;j++)
            if(d[j]>=0 && d[j]<d[i])i=j;
        for(j=0;j<n;j++)
            if(c[i][j]<d[j])
                d[j]=c[i][j],p[j]=i;
        sum+=d[i];
        d[i]=-1;
    }
    return sum;
}
\end{verbatim}

\subsection{Matching}
\begin{verbatim}
const int V=1005;
char p[V],c[V][V];
int t;
char go(int v){
    if(p[v])return 0;
    if(v==t)return 1;
    p[v]=1;
    for(int i=1;i<=t;i++)
        if(c[v][i]-- && go(i))
            return ++c[i][v];
        else c[v][i]++;
    return 0;
}
int flow(){
    int i,j=0;
    for(i=0;i<=t;i++)p[i]=0;
    while(go(0))
        for(j++,i=0;i<=t;i++)p[i]=0;
    return j;
}
\end{verbatim}

\subsection{Matching(Hopcroft-Karp algorithm)}
\begin{verbatim}
const int V=1024,inf=2147483647;
int t,c[V][V],p[V],d[V],u[V],q[V];
int sp(){
    int i,j,k;
    for(i=0;i<=t;i++)
        d[i]=inf;
    d[q[0]=t]=0;
    for(i=0,j=1;d[0]>=inf && i<j;i++)
        for(k=0;k<=t;k++)
            if(c[k][q[i]] && d[k]>=inf)
                d[q[j++]=k]=d[q[i]]+1;
    return d[0];
}
int go(int v){
    if(v==t)return 1;
    int sum=0;
    for(;u[v]<=t;u[v]++)
        if(d[v]==d[u[v]]+1){
            if(c[v][u[v]]-- && go(u[v])){
                c[u[v]][v]++;
                if(v)return 1;
                sum++;
            }
            else c[v][u[v]]++;
        }
    return sum;
}
int flow(){
    int i,sum=0;
    while(sp()<inf){
        for(i=0;i<=t;i++)u[i]=0;
        sum+=go(0);
    }
    return sum;
}
\end{verbatim}
\subsection{Max-Flow}
\begin{verbatim}
const int MaxV=200;
struct list{
    int v;
    list *prev,*next;
}*head;
int t,h[MaxV],e[MaxV],n[MaxV],c[MaxV][MaxV];
inline int min(int a,int b){
    if(a<b)return a;
    return b;
}
void makelist(){
    int i;
    list *ptr;
    head=new list;
    head->prev=head->next=NULL;
    ptr=head;
    for(i=1;i<t-1;i++,ptr=ptr->next){
        ptr->v=i;
        ptr->next=new list;
        ptr->next->prev=ptr;
    }
    ptr->v=t-1;
    ptr->next=NULL;
}
void cleanlist(list *&ptr=head){
    if(ptr){
        cleanlist(ptr->next);
        delete ptr;
        ptr=NULL;
    }
}
void tofront(list *v){
    v->prev->next=v->next;
    if(v->next!=NULL)
        v->next->prev=v->prev;
    v->next=head;
    head->prev=v;
    v->prev=NULL;
    head=v;
}
void push(int v,int u){
    int f=min(c[v][u],e[v]);
    e[v]-=f;
    e[u]+=f;
    c[v][u]-=f;
    c[u][v]+=f;
}
void relabel(int v){
    int i,min;
    for(i=0,min=2*t;i<=t;i++)
        if(c[v][i]>0 && h[i]+1<min)
            min=h[i]+1;
    h[v]=min;
}
void discharge(int v){
    while(e[v]>0){
        if(n[v]>t)
            relabel(v),n[v]=0;
        else if(c[v][n[v]]>0 && h[v]==h[n[v]]+1)
            push(v,n[v]);
        else n[v]++;
    }
}
int flow(){
    int i,v,lh;
    list *ptr;
    for(i=0;i<=t;i++)h[i]=n[i]=e[i]=0;
    for(i=0;i<=t;i++){
        if(c[0][i]==0)
            continue;
        e[i]=c[0][i];
        c[0][i]-=e[i];
        c[i][0]+=e[i];
    }
    h[0]=t+1;
    makelist();
    for(ptr=head;ptr!=NULL;ptr=ptr->next){
        v=ptr->v;
        lh=h[v];
        discharge(v);
        if(h[v]>lh && head!=ptr)
            tofront(ptr);
    }
    return e[t];
    cleanlist();
}
\end{verbatim}

\subsection{Min-cost Matching}
\begin{verbatim}
const long long inf=9223372036854775807ll;
const int V=100;
char u[V];
int n,p[V],q[V*V],cap[V][V],cost[V][V];
long long d[V+1];
long long sp(){
    int i,j,k;
    for(i=0;i<n;i++)d[i]=inf,u[i]=1;
    q[0]=d[0]=u[0]=0;
    for(i=0,j=1;i<j;i++){
        u[q[i]]=1;
        for(k=0;k<n;k++){
            if(cap[q[i]][k]==2 && d[q[i]]-cost[k][q[i]]<d[k]){
                d[k]=d[p[k]=q[i]]-cost[k][q[i]];
                if(u[k])u[q[j++]=k]=0;
            }
            if(cap[q[i]][k]==1 && d[q[i]]+cost[q[i]][k]<d[k]){
                d[k]=d[p[k]=q[i]]+cost[q[i]][k];
                if(u[k])u[q[j++]=k]=0;
            }
        }
    }
    if(d[n-1]<inf)return d[n-1];
    return -1;
}
long long flow(int m){
    long long tmp,sum=0;
    while(m>0 && (tmp=sp())>=0){
        sum+=tmp;
        m--;
        for(int i=n-1;i>0;i=p[i])
            cap[p[i]][i]--,cap[i][p[i]]++;
    }
    return sum;
}
\end{verbatim}

\section{Search}

\subsection{Sticks}
\begin{verbatim}
int y,n,m,min,max,use[51],num[51],able[10000];
void dfs(int len,int d,int i){
   if(y)return;
   if(!d){
       y=1;
       return;
   }
   if(!len){
       while(!use[i])i--;
       use[i]--;
       if(i==m)
           dfs(0,d-1,max);
       else if(i+min<=m)
           dfs(i,d,i);
       use[i]++;
       return;
   }
   for(;i>0 && !y;i--)
       if(use[i] && i+len<=m){
           use[i]--;
           if(len+i==m){
               dfs(0,d-1,max);
               use[i]++;
               return;
           }
           else if(i+min<=m)
               dfs(len+i,d,i);
           use[i]++;
       }
}
main(){
int i,k,sum,stick;
while(scanf("%d",&n) && n){
   for(min=51,max=i=sum=0;i<n;i++){
       scanf("%d",&stick);
       sum+=stick;
       num[stick]++;
       max>?=stick;
       min<?=stick;
   }
   for(y=0,i=max;!y && i<=50;i++)
       if(sum%i==0){
           m=i;
           for(k=1;k<=50;k++)use[k]=num[k];
           dfs(0,sum/i,max);
       }
   printf("%d\n",y?m:sum);
}
}
\end{verbatim}

\subsection{15 puzzle(IDA*)}
\begin{verbatim}
#define vaild(x,y) (x>=0 && x<n && y>=0 && y<n)
const int n=4,dx[]={1,0,-1,0},dy[]={0,1,0,-1},rev[]={2,3,0,1};
char path[1000],dirt[]="DRUL";
int x,y,step,score,next,bound,s[n][n],num[n*n][n][n];
bool dfs(){
    if(step+score>bound){
        if(step+score<next)
            next=step+score;
        return false;
    }
    if(!score){
        return true;
        path[step]=0;
    }
    for(int i=0;i<4;i++)
        if(path[step-1]!=dirt[rev[i]] && vaild(x+dx[i],y+dy[i]))        {
            score-=num[s[x][y]][x][y];
            s[x+dx[i]][y+dy[i]]=s[x][y];
            s[x+=dx[i]][y+=dy[i]]=0;
            score+=num[s[x][y]][x][y];
            path[step++]=dirt[i];
            if(dfs())
                return true;
            step--;
            score-=num[s[x][y]][x][y];
            s[x-dx[i]][y-dy[i]]=s[x][y];
            s[x-=dx[i]][y-=dy[i]]=0;
            score+=num[s[x][y]][x][y];
        }
    return false;
}
main(){
    int i,j,k,l,t;
    scanf("%d",&t);
    for(k=n*n-2;k>=0;k--)
        for(i=0;i<n;i++)
            for(j=0;j<n;j++)
                num[k+1][i][j]=abs(k/n-i)+abs(k%n-j);
    while(t--){
        for(i=l=score=0;i<n;i++)
            for(j=0;j<n;j++){
                scanf("%d",&s[i][j]);
                if(s[i][j]==0){
                    x=i,y=j;
                    continue;
                }
                score+=num[s[i][j]][i][j];
                for(k=i*n+j;k>=0;k--)
                    if(s[k/n][k%n]>s[i][j])l++;
            }
        if((l+x+1)&1){
            puts("This puzzle is not solvable.");
            continue;
        }
        step=1,bound=score;
        while(1){
            next=1000;
            if(dfs())break;
            bound=next;
        }
        puts(path);
    }
}

\end{verbatim}

\section{Mathematics}
\subsection{Factorization and Primality Test}
\begin{verbatim}
#include<cmath>
#include<cstdio>
#include<algorithm>
using namespace std;
long long Rand(){
    return rand()*(1ll<<48)+rand()*(1ll<<32)+rand()*(1ll<<16)+rand();
}
long long mul(long long a,long long b,long long m){
    long long i,res=0;
    for(i=1;i<=b;i*=2,(a*=2)%=m)
        if(b&i)(res+=a)%=m;
    return res;
}
long long pow(long long n,long long k,long long m){
    if(k==0)return 1;
    if(k%2==1)
        return mul(n,pow(n,k-1,m),m);
    n=pow(n,k/2,m);
    return mul(n,n,m);
}
bool witness(long long a,long long n){
    long long x,y,u,t;
    for(u=n-1,t=0;u%2==0;u/=2,t++);
    x=pow(a,u,n);
    while(t--){
        y=x;
        x=pow(x,2,n);
        if(x==1 && y!=1 && y!=n-1)
            return 1;
    }
    return x!=1;
}
bool mr(long long n,int s=25){
    if(n-1>=2 && witness(2,n))return 0;
    if(n-1>=3 && witness(3,n))return 0;
    if(n-1>=7 && witness(7,n))return 0;
    if(n-1>=61 && witness(61,n))return 0;
    if(n-1>=24251 && witness(24251,n))return 0;
    if(n==46856248255981ll)return 0;
    return 1;
}
long long gcd(long long a,long long b){
    while((a%=b)&&(b%=a));
    return a+b;
}
namespace g{long long abs(long long x){return x<0?-x:x;}}
int _c=1;
long long _f(long long x,long long n)
{return(mul(x,x,n)+_c)%n;}
long long go(long long n){
    long long x,y,d=1;
        x=y=Rand()%n;
        while(d==1){
            x=_f(x,n);
            y=_f(_f(y,n),n);
            d=gcd(g::abs(y-x),n);
        }
        if(d!=n)return d;
    return d;
}
void fa(long long n,int& fn,long long s[]){
    long long x;
    while(n>1 && n%2==0)
        s[fn++]=2,n/=2;
    while(!mr(n)){
        for(_c=1,x=n;x==n;_c=1+Rand()%(n-1))x=go(n);
        if(x<0)break;
        n/=x;
        fa(x,fn,s);
    }
    if(n>1)s[fn++]=n;
}
main(){
    int i,j,m;
    long long n,k,s[70];
    while(scanf("%I64d",&n)==1){
        m=0;
        while(n%2==0)n>>=1;
        fa(n,m,s);
        std::sort(s,s+m);
        for(i=0,k=1;i<m;i+=j){
            for(j=0;i+j<m && s[i+j]==s[i];j++);
            k*=j+1;
        }
        printf("%I64d\n",k);
    }
}

\end{verbatim}

\subsection{Permutation}
\begin{verbatim}
#include<algorithm>
long long f[50];
long long go(int num[],int n,int t){
    int i,j,k;
    long long s1[25],s2[25];
    if(n<=1)return 1;
    for(j=0;j<=t;j++)s1[j]=0;
    for(j=0;j<=num[0] && j<=t;j++)
        s1[j]=f[t]/f[j];
    for(i=1;i<n;i++){
        for(j=0;j<=t;j++)s2[j]=0;
        for(j=0;j<=num[i] && j<=t;j++)
            for(k=0;j+k<=t;k++)
                s2[j+k]+=s1[k]/f[j];
        for(j=0;j<=t;j++)s1[j]=s2[j];
    }
    return s1[t];
}
int count(int s[],int n,int num[]){
    int i,j;
    std::sort(s,s+n);
    for(i=j=0;i<n;j++)
    {
        s[j]=s[i];
        for(num[j]=0;i<n && s[i]==s[j];i++)num[j]++;
    }
    return j;
}
void make(int s1[],int u1[],const int& n1,int s2[],int n2,long long k){
    int i,j;
    long long l;
    for(i=0;i<n2;i++)
        for(j=0;j<n1;j++)
        {
            if(!u1[j])continue;
            s2[i]=s1[j],u1[j]--;
            l=go(u1,n1,n2-i-1);
            if(k<=l)break;
            k-=l,u1[j]++;
        }
}
long long get(int s1[],int u1[],int n1,int s2[],int n2){
    int i,j;
    long long k=0;
    for(i=0;i<n2;i++)
        for(j=0;j<n1;j++)
        {
            u1[j]--;
            if(s2[i]==s1[j])break;
            k+=go(u1,n1,n2-i-1);
            u1[j]++;
        }
    return k;
}
\end{verbatim}

\subsection{Huge Mod}
\begin{verbatim}
#include<cstdio>
struct sint{
    int n,m,k;
    sint(int a=0):n(a){}
    void operator*=(sint a){
        n*=a.n;
        if(n>k)n=k+(n-k)%m;
    }
    bool operator==(sint a){return n==a.n;}
}s[100];
int n,m[10],u[20000];
int go(int d){
    if(d>=n)return 1;
    int i,j;
    sint x=s[d];
    x.n=1,x*=s[d];
    for(j=0;j<=x.k+x.m;j++)u[j]=-1;
    for(i=1;;i++){
        if(u[x.n]>=0)break;
        u[x.n]=i;
        x*=s[d];
    }
    s[d+1].k=u[x.n];
    s[d+1].m=i-u[x.n];
    j=go(d+1);
    for(x.n=1;j--;x*=s[d]);
    return x.n;
}
main()
{
    int i,C=1;
    while(scanf("%d %d",&s[0].m,&n)==2){
        s[0].k=0;
        for(i=0;i<n;i++)
            scanf("%d",&s[i].n);
        printf("Case #%d: %d\n",C++,go(0));
    }
}
\end{verbatim}

\subsection{Recurrence}
\begin{verbatim}
#include<stdio.h>
class martix{
public:
    int n,m,s[20][20];
    void clean(int d){
        int i,j;
        for(i=0;i<d;i++)
            for(j=0;j<d;j++)
                s[i][j]=0;
    }
    void operator*=(martix b){
        martix a=*this;
        int i,j,k;
        for(i=0;i<n;i++)
            for(j=0;j<n;j++){
                s[i][j]=0;
                for(k=0;k<n;k++){
                    s[i][j]+=(a.s[i][k]*b.s[k][j])%m;
                    s[i][j]%=m;
                }
            }
    }
    void print(){
        int i,j;
        for(i=0;i<n;i++){
            printf("%d",s[i][0]);
            for(j=1;j<n;j++)
                printf(" %d",s[i][j]);
            puts("");
        }
    }
}s,r;
main(){
    int i,j,d,n,m,a[20],f[20];
    while(scanf("%d %d %d",&d,&n,&m) && d+n+m){
        for(i=0;i<d;i++){
            scanf("%d",&a[i]);
            a[i]%=m;
        }
        for(i=0;i<d;i++){
            scanf("%d",&f[i]);
            f[i]%=m;
        }
        if(n<=d){
            printf("%d\n",f[n-1]);
            continue;
        }
        s.clean(d),r.clean(d);
        s.m=r.m=m;
        s.n=r.n=d;
        for(i=0;i<d;i++){
            s.s[i][i]=1;
            if(i)r.s[i-1][i]=1;
            r.s[d-1][d-i-1]=a[i];
        }
        for(i=1,n-=d;i<=n && i>0;i<<=1,r*=r)
            if(i&n)s*=r;
        for(i=n=0;i<d;i++)
            n=(n+s.s[d-1][i]*f[i])%m;
        printf("%d\n",n);
    }
}

\end{verbatim}

\section{Strings}
\subsection{Knuth-Morris-Pratt algorithm}

\begin{verbatim}
#include<cstdio>
main(){
    int i,j,p[1001]={0,0};
    char s1[1001],s2[1001];
    while(scanf("%s %s",s1,s2)>0){
        for(i=0;s1[i];i++);
        s1[i++]='$',s1[i]=0;
        for(i=1,j=0;s1[i];i++){
            while(j && s1[i]!=s1[j])j=p[j];
            if(s1[i]==s1[j])j++;
            p[i+1]=j;
        }
        for(i=j=0;s2[i];i++){
            while(j && s1[j]!=s2[i])j=p[j];
            if(s1[j]==s2[i])j++;
        }
        printf("%d\n",j);
    }
}

\end{verbatim}

\subsection{Extended KMP}

\begin{verbatim}
#include<cstdio>
#include<cstring>
struct node{
    node *sub,*c[26];
    int b;
}*root,*ptr1[100],*ptr2[100];
int to[256],now[1001],next[101],c[101][101];
char s[1000][1001],p[100][101];
void clear(node **ptr){
    if(*ptr){
        for(int i=0;i<26;i++)
            clear(&(*ptr)->c[i]);
        delete *ptr;
        *ptr=NULL;
    }
}
int build(node *&ptr,char *a,int b){
    if(!ptr){
        ptr=new node;
        for(int i=0;i<26;i++)
            ptr->c[i]=NULL;
        ptr->b=-1;
    }
    if(*a) return build(ptr->c[to[*a]],a+1,b);
    if(ptr->b>=0) return ptr->b;
    return(ptr->b=b);
}
main(){
    node *ptr;
    int i,j,n,m,t,sum;
    for(i='a';i<='z';i++)
        to[i]=i-'a';
    scanf("%d",&t);
    while(t--){
        clear(&root);
        scanf("%d %d",&n,&m);
        for(i=0;i<n;i++)
            scanf("%s",s[i]);
        scanf("%d %d",&m,&j);
        for(i=0;i<m;i++){
            next[i]=0;
            scanf("%s",p[i]);
            for(j=0;j<=i;j++)
                c[i][j]=c[j][i]=!strcmp(p[i],p[j]);
            j=build(root,p[i],i);
        }
        for(i=1,j=0;i<m;i++){
            while(j>0 && !c[i][j])
                j=next[j];
            j+=c[i][j];
            next[i+1]=j;
        }
        for(i=0;i<m;i++){
            ptr1[i]=root->c[to[p[i][0]]];
            ptr2[i]=root;
            ptr1[i]->sub=ptr2[i];
        }
        for(j=1;p[0][j];j++)
            for(i=0;i<m;i++){
                ptr1[i]=ptr1[i]->c[to[p[i][j]]];
                while(ptr2[i]!=root && !ptr2[i]->c[to[p[i][j]]])
                    ptr2[i]=ptr2[i]->sub;
                if(ptr2[i]->c[to[p[i][j]]])
                    ptr2[i]=ptr2[i]->c[to[p[i][j]]];
                ptr1[i]->sub=ptr2[i];
                if(ptr2[i]->b>0)
                    ptr1[i]->b=ptr2[i]->b;
            }
        for(j=0;s[0][j];j++)
            now[j]=0;
        for(i=sum=0;i<n;i++)
            for(j=0,ptr=root;s[i][j];j++){
                while(ptr!=root && !ptr->c[to[s[i][j]]])
                    ptr=ptr->sub;
                if(ptr->c[to[s[i][j]]])
                    ptr=ptr->c[to[s[i][j]]];
                if(ptr->b<0){
                    now[j]=0;
                    continue;
                }
                while(now[j]>0 && !c[ptr->b][now[j]])
                    now[j]=next[now[j]];
                if(c[ptr->b][now[j]])
                    now[j]++;
                if(now[j]==m)
                    sum++;
            }
        printf("%d\n",sum);
    }
}
\end{verbatim}

\subsection{Suffix Array}
\begin{verbatim}
#include<cstdio>
const int maxn=200000;
inline bool leq(int a1,int a2,int b1,int b2) // lexicographic order
{return(a1<b1||a1==b1 && a2<=b2);} // for pairs
inline bool leq(int a1,int a2,int a3,int b1,int b2,int b3)
{return(a1<b1 || a1==b1 && leq(a2,a3, b2,b3));} // and triples
// stably sort a[0..n-1] to b[0..n-1] with keys in 0..K from r
int c[maxn+50];
static void radixPass(int a[],int b[],int r[],int n,int K)
{// count occurrences
    for(int i=0;i<=K;i++)c[i]=0; // reset counters
    for(int i=0;i<n;i++)c[r[a[i]]]++; // count occurrences
    for(int i=0,sum=0;i<=K;i++) // exclusive prefix sums
    {int t=c[i];c[i]=sum;sum+=t;}
    for(int i=0;i<n;i++)b[c[r[a[i]]]++]=a[i]; // sort
}
// find the suffix array SA of s[0..n-1] in {1..K}^n
// require s[n]=s[n+1]=s[n+2]=0, n>=2
void suffixArray(int s[],int SA[],int n,int K)
{
    int n0=(n+2)/3,n1=(n+1)/3,n2=n/3,n02=n0+n2;
    int *s12 =new int[n02+3];s12[n02]=s12[n02+1]=s12[n02+2]=0;
    int *SA12=new int[n02+3];SA12[n02]=SA12[n02+1]=SA12[n02+2]=0;
    int *s0  =new int[n0];
    int *SA0 =new int[n0];
// generate positions of mod 1 and mod 2 suffixes
// the "+(n0-n1)" adds a dummy mod 1 suffix if n%3 == 1
    for(int i=0,j=0;i<n+(n0-n1);i++)if(i%3!=0)s12[j++]=i;
// lsb radix sort the mod 1 and mod 2 triples
    radixPass(s12,SA12,s+2,n02,K);
    radixPass(SA12,s12,s+1,n02,K);
    radixPass(s12,SA12,s,n02,K);
// find lexicographic names of triples
    int name=0,c0=-1,c1=-1,c2=-1;
    for(int i=0;i<n02;i++){
        if(s[SA12[i]]!=c0 || s[SA12[i]+1]!=c1 || s[SA12[i]+2]!=c2)
           {name++;c0=s[SA12[i]];c1=s[SA12[i]+1];c2=s[SA12[i]+2];}
        if(SA12[i]%3==1)s12[SA12[i]/3]=name; // left half
        else s12[SA12[i]/3+n0]=name;  // right half
    }
// recurse if names are not yet unique
    if(name<n02){
        suffixArray(s12,SA12,n02,name);
// store unique names in s12 using the suffix array
        for(int i=0;i<n02;i++)s12[SA12[i]]=i+1;
    }else // generate the suffix array of s12 directly
        for(int i=0;i<n02;i++)SA12[s12[i]-1]=i;
// stably sort the mod 0 suffixes from SA12 by their first character
    for(int i=0,j=0;i<n02;i++)if(SA12[i]<n0)s0[j++]=3*SA12[i];
    radixPass(s0,SA0,s,n0,K);
// merge sorted SA0 suffixes and sorted SA12 suffixes
    for(int p=0,t=n0-n1,k=0;k<n;k++){
#define GetI() (SA12[t] < n0 ? SA12[t]*3+1: (SA12[t] - n0)*3+2)
        int i=GetI(); // pos of current offset 12 suffix
        int j=SA0[p]; // pos of current offset 0 suffix
        if(SA12[t]<n0? // different compares for mod 1 and mod 2 suffixes
            leq(s[i],s12[SA12[t]+n0],s[j],s12[j/3]):
            leq(s[i],s[i+1],s12[SA12[t]-n0+1],s[j],s[j+1],s12[j/3+n0]))
        {// suffix from SA12 is smaller
            SA[k]=i;t++;
            if(t==n02) // done --- only SA0 suffixes left
            for(k++;p<n0;p++,k++)SA[k]=SA0[p];
        }else{// suffix from SA0 is smaller
            SA[k]=j;p++;
            if(p==n0) // done --- only SA12 suffixes left
            for(k++;t<n02;t++,k++)SA[k]=GetI();
        }
    }
    delete[] s12; delete[] SA12; delete[] SA0; delete[] s0;
}

int n,s[maxn],t[maxn],d[maxn],x[maxn],ml[][maxn],mr[][maxn],ub[65537];
void go(int s[],int t[],int d[],int n){
    int i,j,k;
    for(i=0;i<n;i++)x[t[i]]=i;
    for(i=j=0;i<n;i++){
        if(x[i]==n-1)
        {j=d[x[i]]=0;continue;}
        k=t[x[i]+1];
        while(s[i+j]==s[k+j])
            j++;
        d[x[i]]=j;
        j-=(j>0);
    }
}
void prermq(int z[],int ml[][maxn],int mr[][maxn],int n){
    int i,j,k,p;
    for(i=1,p=0;i<=n;i*=2,p++){
        for(j=0;j<n;j+=i){
            ml[p][j]=z[j];
            for(k=j+1;k<j+i;k++)
                ml[p][k]=(z[k]<?ml[p][k-1]);
            mr[p][j+i-1]=z[j+i-1];
            for(k=j+i-2;k>=j;k--)
                mr[p][k]=(z[k]<?mr[p][k+1]);
        }
    }
}
char tmp[maxn];
int lcp(int i,int j){
    if(i>=n || j>=n || i<0 || j<0){
        printf("%d %d",i,j);
        scanf(" ");
        return 0;
    }
    i=x[i],j=x[j];
    if(i>j)i^=j^=i^=j;
    j--;
    int k=ub[i^j];
    return (mr[k][i])<?(ml[k][j]);
}
int find(int v,int l1,int l2){
    if(!lcp(v-l1,v))return v;
    int i,j,k=0,last=lcp(v-l1,v);
    for(i=0,j=(l2-1)<?(v-l1);i<=j;){
        k=(i+j)/2;
        if(lcp(v-l1-k,v-k)!=last+k)j=k-1;
        else if(v-l1-k-1>=0 && lcp(v-l1-k-1,v-k-1)==last+k+1)i=k+1;
        else break;
    }
    if(lcp(v-l1-k,v-k)<l2)
        return v;
    return v-k;
}
main()
{
    int i,j,k,l,g,max,T,C=1;
    for(i=1,k=0;i<65536;i*=2,k++)
        for(j=i*2-1;j>=i;j--)ub[j]=k;
    while(scanf("%d",&n)==1)
    {
        scanf("%d%c",&g,tmp);
        gets(tmp);
        for(n=0;tmp[n];n++)
            s[n]=tmp[n]-'a'+1;
        s[n]=s[n+1]=s[n+2]=0;
        suffixArray(s,t,n,26);
        go(s,t,d,n);
        for(i=j=0;i<n;i++)
             j>?=d[i];
        printf("%d\n",j);
				prermq(d,ml,mr,n-1);
        for(i=max=0;i<n;i++)max>?=d[i];
        for(i=1+g,k=0;max+g>=i && i<n;i++)
            for(j=i;j<n;j+=i-g){
                j=find(j,i,i-g);
                l=lcp(j-i,j);
                if(l+g>=i)k+=l+g-i+1;
                if(l>0)j+=l-1;
            }
        printf("Case %d: %d\n",C++,k);*/
    }
}

\end{verbatim}
\section{Misc.}
\subsection{Date}
\begin{verbatim}
int tonum(int y,int m,int d){
    static int day[]={0,31,28,31,30,31,30,31,31,30,31,30,31};
    y--;
    int num=y*365+y/4-y/100+y/400;
    y++;
    if((y%4==0 && y%100)|| y%400==0)day[2]=29;
    else day[2]=28;
    for(int i=1;i<m;i++)
        num+=day[i];
    return num+=d;
}
void todate(int num,int &y,int &m,int &d){
    static int y400=146097,y100=36524,y4=1461,
        day[]={0,31,28,31,30,31,30,31,31,30,31,30,31};;
    num--;
    y=num/y400*400;
    num%=y400;
    y+=num/y100*100;
    num%=y100;
    y+=num/y4*4;
    num%=y4;
    y+=num/365;
    num%=365;
    for(m=1;num>=day[m];num-=day[m++]);
    d=++num;
}
\end{verbatim}
\end{document}