\documentclass{report}
\usepackage{color}
\definecolor{light}{gray}{.93}
\usepackage[plainpages=false,pdftex,colorlinks,backref]{hyperref}
\usepackage{graphicx}

\title{Generic Distribution and Filtering Algorithms}
\author{Larry Bush $<$bushl2@cs.rpi.edu$>$\\Dan Jemiolo $<$jemiod@rpi.edu$>$\\Kyle Ross $<$rossk2@rpi.edu$>$\\Dave Siebecker $<$siebed@cs.rpi.edu$>$\\David R. Musser $<$musser@cs.rpi.edu$>$}
\date{8 December 2002}

\newcommand{\first}{\mbox{\texttt{first}}}
\newcommand{\last}{\mbox{\texttt{last}}}
\newcommand{\predTRUE}{\mbox{\texttt{predTRUE}}}
\newcommand{\predFALSE}{\mbox{\texttt{predFalse}}}

%created by KR ... this way we can switch how we represent code later, if we need to; I like this better than hard-coding \texttt
\newcommand{\code}[1]{\texttt{#1}}

% Following command is for comments or questions by me.
% leave this command in for my future use but remove all uses of it 
% (after adding or correcting text to take care of the noted problem)
\newcommand{\dm}[1]{{\bf {$\langle$DM: #1$\rangle$}}}

\begin{document}

\maketitle

\begin{abstract}
A generic software library is presented to solve the problem of 
classifying objects based on user-defined criteria and distributing 
the objects based on this classfication. Along with documented 
versions of the source code, a comprehensive discussion of the 
library is made from several perspectives: The user's guide \& 
tutorial and the reference manual help the reader to quickly begin to 
use the library. A discussion of the design issues involved in the 
creation of the library provides future software designers the 
insight required to extend the library. A lengthy set of tests and 
results assures the user that the library operates correctly and 
efficiently.
\end{abstract}

\tableofcontents

\newpage

\chapter{User's Guide}
\label{sec-user-guide}

\section{Introduction}

\subsection{Overview}
\label{sec-overview}
It is often useful to take a set of items and distribute the elements 
of this set into two or more destinations based on some sort of 
decision schema. If this schema is phrased as a sequence of 
predicates paired with \code{OutputIterator}s then a generalised view 
of this problem can be solved by a small set of components that work 
together to filter elements from a batch of data into one or more 
destinations based on a collection of user-defined predicates.

Input is specified with either a single \code{InputIterator} (to 
specify a single element) or a pair of \code{InputIterator}s (to 
signify a range of elements); the various output destinations and 
their associated predicates will be supplied by creating one or more 
\code{functor} classes derived from an abstract base class within the 
framework. Our components work seamlessly with C++ Standard Library 
containers and streams, since all communication with them will be 
through \code{Input}- and \code{OutputIterator}s. In order to be as 
generic and flexible as possible, the interfaces will have to make 
extensive use of member template functions --- this means that our 
work will be limited to the GNU C++ compiler, as Microsoft's Visual 
Studio does not yet support this important language 
feature.\footnote{Use of a compiler front-end --- like those 
developed by Comeau Computing --- would allow use of compilers such 
as Microsoft's that are grossly non-compliant with the C++ standard.}

\subsection{Document Conventions}
Since English words like ``destination'' and ``router'' have numerous 
meanings (the latter, particularly, in the computing sciences), 
explicit textual formatting will be used to differentiate between 
abstract ideas and concrete C++ types or concepts based on normal 
text for the former and \code{special text} for the latter. For 
example: in the context of this discussion, it is quite useful to 
differentiate between an abstract destination (a place where output 
is being sent: possibly a member of a sub-type of the 
\code{destination} class, possibly an \code{OutputIterator}, etc.) 
and the \code{destination} class as defined by the Generic 
Distribution and Filtering Algorithms Library. This should make it 
significantly easier to understand the present report.

\subsection{The Generic Distribution and Filtering Algorithms Library}
To solve the problem described in Section \ref{sec-overview}, the 
Generic Distribution and Filtering Algorithms Library (henceforth 
referenced as ``GDFA Library'') has been developed. Conceptually, the 
GDFA Library  consists in three main components: the trivial 
\code{distribute} function, the \code{destination} base class, and 
the \code{router} class. As mentioned supra, each of these is 
templated to allow for the greatest possible generality, making the 
library useful over a varied domain of computing problems.

\subsubsection{The \code{distribute} Function}
The \code{distribute} function solves the trivial case of the general 
filtering problem: an input range is to be distributed to two output 
destinations based upon element-wise application of a single 
predicate --- elements for which the predicate returns \code{true} 
are output to one destination; all other elements are output to a 
second destination.

\subsubsection{The \code{destination} Base Class}
The \code{destination} class is an abstract class from which users of 
the GDFA Library may inherit in defining their own destinations, 
which conceptually model the pairing of a predicate and an 
\code{OutputIterator}, as described in Section \ref{sec-overview}. 
\code{destinations} have a \code{distribute} method (not to be 
confused with the trivial \code{distribute} function) which takes an 
element, applies a predicate, takes an appropriate action, and 
returns \code{false} if and only if the element should be passed to 
the following \code{destination}. This is explained in much greater 
detail in Section \ref{sec-apiref} and is demonstrated by example in 
Section \ref{sec-tutorial}.

\subsubsection{The \code{router} Class}
For the more general case of the problem, the GDFA Library defines a 
\code{router} class. This class stores and prioritises 
\code{destination}s and provides a convenient and re-usable way to 
apply an arbitrarily large number of destinations in a specified 
order to an input sequence. The \code{distribute} method takes a 
range of elements and applies the filtering order implicitly defined 
by the \code{destination}s; hence a single \code{router} can be 
defined and used to filter \emph{multiple} sequences of elements. The 
general schema for doing so is: create a \code{router}, add 
appropriate \code{destination}s to that \code{router}, call the 
\code{distribute} method for each sequence to be filtered. Again, a 
more detailed explanation can be found in Section \ref{sec-apiref} 
and some practical examples in Section \ref{sec-tutorial}.

\section{Tutorial}
\label{sec-tutorial}
This tutorial contains a number of ``learn by example'' programmes 
that are explained in some detail, each of which illustrates a 
different aspect of using the GDFA Library. The database example in 
Section \ref{sec-database-example} illustrates a use of the trivial 
\code{distribute} function. The sporting goods store example in 
Section \ref{sec-sports-store-example} demonstrates creation of 
\code{destination}s and use of the \code{router} class in performing 
a fairly simple single-destination\footnote{``Single-destination'' 
refers to the fact that each element will be placed in at most (or, 
in the case, exactly) on \code{destination}.} filtering task. 
Finally, the criminal profiling example in Section 
\ref{sec-criminal-example} demonstrates use of a complex 
multi-tier\footnote{``Multi-tier'' refers to the fact that the input 
data are filtered and then the results of this filtering are 
\emph{again} filtered and so on.} filtering application.

\subsection{The Database Example}
\label{sec-database-example}
A simple example using the trivial \code{distribute} function is to 
filter database jobs by priority: database jobs each have a priority 
from the set $\lbrace 1,2,3,4,5\rbrace$ where $1$ is low priority and 
$5$ is high priority. We want to separate out just the jobs that are 
designated high-priority. These jobs will be run first, followed by 
all of the other jobs. In this small example, we, of course, are not 
actually going to do anything with our jobs, but the idea could 
easily be extended and implemented for a real database.

Here is an overview of the programme we will use to solve the problem:

\begin{flushleft} \small \label{part1}
\verb@"run-database-jobs.cpp"@ {\footnotesize \hypertarget{6}{6} }$\equiv$
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@#include <iostream>@\\
\mbox{}\verb@#include <string>@\\
\mbox{}\verb@#include <fstream>@\\
\mbox{}\verb@#include <vector>@\\
\mbox{}\verb@#include <iterator>@\\
\mbox{}\verb@#include <functional>@\\
\mbox{}\verb@@\\
\mbox{}\verb@#include "router.hpp"@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\hbox{\colorbox{light}{$\langle$define database job {\footnotesize \hyperlink{7a}{7a}}$\rangle$}}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@int main()@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  std::vector<DatabaseJob> urgentJobs;@\\
\mbox{}\verb@  std::vector<DatabaseJob> normalJobs;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  @\hbox{\colorbox{light}{$\langle$read and filter the jobs {\footnotesize \hyperlink{9a}{9a}}$\rangle$}}\verb@@\\
\mbox{}\verb@  @\hbox{\colorbox{light}{$\langle$execute the jobs {\footnotesize \hyperlink{10a}{10a}}$\rangle$}}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@  return EXIT_SUCCESS;@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@
\end{list}
\vspace{-2ex}
\end{flushleft}
A simple class to represent a database job is required. It must 
provide storage of the job's name, its priority, and its PID. We need 
functionality to access the priority-level, check if the job is 
high-priority or not, check if the job has finished running, compare 
two jobs by priority, and run the job. We define an input operator as 
a \code{friend}.

\begin{flushleft} \small
\begin{minipage}{\linewidth}\color{blue} \label{part2}
\colorbox{light}{$\langle$define database job {\footnotesize \hypertarget{7a}{7a}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@class DatabaseJob@\\
\mbox{}\verb@{@\\
\mbox{}\verb@public:@\\
\mbox{}\verb@  @\hbox{\colorbox{light}{$\langle$priority-level accessor {\footnotesize \hyperlink{7b}{7b}}$\rangle$}}\verb@@\\
\mbox{}\verb@  @\hbox{\colorbox{light}{$\langle$is the job high-priority? {\footnotesize \hyperlink{7c}{7c}}$\rangle$}}\verb@@\\
\mbox{}\verb@  @\hbox{\colorbox{light}{$\langle$is the job finished? {\footnotesize \hyperlink{8a}{8a}}$\rangle$}}\verb@@\\
\mbox{}\verb@  @\hbox{\colorbox{light}{$\langle$run the job {\footnotesize \hyperlink{8b}{8b}}$\rangle$}}\verb@@\\
\mbox{}\verb@  @\hbox{\colorbox{light}{$\langle$compare jobs by priority {\footnotesize \hyperlink{8c}{8c}}$\rangle$}}\verb@@\\
\mbox{}\verb@  friend std::istream& operator>>(std::istream& in,@\\
\mbox{}\verb@                                   DatabaseJob& job);@\\
\mbox{}\verb@@\\
\mbox{}\verb@private:@\\
\mbox{}\verb@  std::string m_scriptName;@\\
\mbox{}\verb@  int m_priorityLevel;@\\
\mbox{}\verb@  std::string m_processID;@\\
\mbox{}\verb@};@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\hbox{\colorbox{light}{$\langle$input a job {\footnotesize \hyperlink{8d}{8d}}$\rangle$}}\verb@@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Used in part \hyperlink{6}{6}.
\end{list}
\end{minipage}\\[4ex]
\end{flushleft}
To get the job's priority-level we create an accessor; by convention 
we define priority-levels in the range $[0..5]$.

\begin{flushleft} \small
\begin{minipage}{\linewidth}\color{blue} \label{part3}
\colorbox{light}{$\langle$priority-level accessor {\footnotesize \hypertarget{7b}{7b}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@int PriorityLevel() const@\\
\mbox{}\verb@{ @\\
\mbox{}\verb@  return m_priorityLevel;@\\
\mbox{}\verb@}@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Used in part \hyperlink{7a}{7a}.
\end{list}
\end{minipage}\\[4ex]
\end{flushleft}
Is the job high-priority? We can easily check this by comparing to 
see if the priority is greater than $4$.

\begin{flushleft} \small
\begin{minipage}{\linewidth}\color{blue} \label{part4}
\colorbox{light}{$\langle$is the job high-priority? {\footnotesize \hypertarget{7c}{7c}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@bool IsHighPriority() const@\\
\mbox{}\verb@{ @\\
\mbox{}\verb@  return m_priorityLevel>4; @\\
\mbox{}\verb@}@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Used in part \hyperlink{7a}{7a}.
\end{list}
\end{minipage}\\[4ex]
\end{flushleft}
A job is finished when the process that is executing its tasks exits. 
For the sake of our example, we just return \code{true}.

\begin{flushleft} \small
\begin{minipage}{\linewidth}\color{blue} \label{part5}
\colorbox{light}{$\langle$is the job finished? {\footnotesize \hypertarget{8a}{8a}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@bool IsFinished() const@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  return true;@\\
\mbox{}\verb@}@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Used in part \hyperlink{7a}{7a}.
\end{list}
\end{minipage}\\[4ex]
\end{flushleft}
We create a new process that performs the tasks this job entails; for 
the sake of the example, we just display the job's information.

\begin{flushleft} \small
\begin{minipage}{\linewidth}\color{blue} \label{part6}
\colorbox{light}{$\langle$run the job {\footnotesize \hypertarget{8b}{8b}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@void Execute()@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  std::cout<<m_processID<<"  "<< m_priorityLevel<<std::endl;@\\
\mbox{}\verb@}@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Used in part \hyperlink{7a}{7a}.
\end{list}
\end{minipage}\\[4ex]
\end{flushleft}
In order to compare jobs by priority, we define two comparator 
operators.

\begin{flushleft} \small
\begin{minipage}{\linewidth}\color{blue} \label{part7}
\colorbox{light}{$\langle$compare jobs by priority {\footnotesize \hypertarget{8c}{8c}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@bool operator< (const DatabaseJob& rhs) const@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  return m_priorityLevel<rhs.m_priorityLevel;@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@\\
\mbox{}\verb@bool operator> (const DatabaseJob& rhs) const@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  return m_priorityLevel>rhs.m_priorityLevel;@\\
\mbox{}\verb@}@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Used in part \hyperlink{7a}{7a}.
\end{list}
\end{minipage}\\[4ex]
\end{flushleft}
In order to read jobs from our input file, we create a simple input 
operator. It reads a job's PID and then its priority-level.

\begin{flushleft} \small
\begin{minipage}{\linewidth}\color{blue} \label{part8}
\colorbox{light}{$\langle$input a job {\footnotesize \hypertarget{8d}{8d}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@std::istream& operator>>(std::istream& in, DatabaseJob& job)@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  in>>job.m_processID>>job.m_priorityLevel;@\\
\mbox{}\verb@  return in;@\\
\mbox{}\verb@}@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Used in part \hyperlink{7a}{7a}.
\end{list}
\end{minipage}\\[4ex]
\end{flushleft}
Now that we have defined a simple class to hold a database job, we 
are ready to filter them! We open the database jobs file and filter 
the jobs as we read them.

\begin{flushleft} \small
\begin{minipage}{\linewidth}\color{blue} \label{part9}
\colorbox{light}{$\langle$read and filter the jobs {\footnotesize \hypertarget{9a}{9a}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@std::ifstream inputFile("./nightly-database-routines.txt");@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\hbox{\colorbox{light}{$\langle$handle file error {\footnotesize \hyperlink{9b}{9b}}$\rangle$}}\verb@@\\
\mbox{}\verb@@\hbox{\colorbox{light}{$\langle$filter the jobs {\footnotesize \hyperlink{9c}{9c}}$\rangle$}}\verb@@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Used in part \hyperlink{6}{6}.
\end{list}
\end{minipage}\\[4ex]
\end{flushleft}
If the file listing the jobs is unavailable, we display an error 
message and exit from the programme, indicating failure to the 
operating system.

\begin{flushleft} \small
\begin{minipage}{\linewidth}\color{blue} \label{part10}
\colorbox{light}{$\langle$handle file error {\footnotesize \hypertarget{9b}{9b}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@if (!inputFile)@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  std::cerr<<"No ./nightly-database-routines.txt file"<<std::endl;@\\
\mbox{}\verb@  return EXIT_FAILURE;        @\\
\mbox{}\verb@}@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Used in part \hyperlink{9a}{9a}.
\end{list}
\end{minipage}\\[4ex]
\end{flushleft}
Now that the file is open, we can filter the jobs by priority. The 
trivial version of \code{distribute} will work fine since we are 
splitting the jobs into exactly one of two groups based on the 
evaluation of a single predicate --- the \code{IsHighPriority} method 
defined by the \code{DatabaseJob} class.

\begin{flushleft} \small
\begin{minipage}{\linewidth}\color{blue} \label{part11}
\colorbox{light}{$\langle$filter the jobs {\footnotesize \hypertarget{9c}{9c}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@gdfa::distribute(std::istream_iterator<DatabaseJob>(inputFile),@\\
\mbox{}\verb@                  std::istream_iterator<DatabaseJob>(),@\\
\mbox{}\verb@                  std::back_inserter(urgentJobs),@\\
\mbox{}\verb@                  std::back_inserter(normalJobs),@\\
\mbox{}\verb@                  std::mem_fun_ref(&DatabaseJob::IsHighPriority));@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Used in part \hyperlink{9a}{9a}.
\end{list}
\end{minipage}\\[4ex]
\end{flushleft}
Now that we have the jobs filtered by priority, we can execute them: 
first the high-priority jobs, then all the other jobs. For the sake 
of this example programme, we just print the job information.

\begin{flushleft} \small
\begin{minipage}{\linewidth}\color{blue} \label{part12}
\colorbox{light}{$\langle$execute the jobs {\footnotesize \hypertarget{10a}{10a}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@std::cout << "\n\nUrgentJobs\n\n";@\\
\mbox{}\verb@for(std::vector<DatabaseJob>::iterator i=urgentJobs.begin();@\\
\mbox{}\verb@    i!=urgentJobs.end(); ++i)@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  (*i).Execute();@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@\\
\mbox{}\verb@std::cout << "\n\nNormalJobs\n\n";@\\
\mbox{}\verb@for(std::vector<DatabaseJob>::iterator i=normalJobs.begin();@\\
\mbox{}\verb@    i!=normalJobs.end(); ++i)@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  (*i).Execute();@\\
\mbox{}\verb@}@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Used in part \hyperlink{6}{6}.
\end{list}
\end{minipage}\\[4ex]
\end{flushleft}
To complete our discussion of this example, all we need is a data 
file.

\begin{flushleft} \small \label{part13}
\verb@"nightly-database-routines.txt"@ {\footnotesize \hypertarget{10b}{10b} }$\equiv$
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@JobTypeA 2 JobTypeA 2 JobTypeH 5 JobTypeH 5@\\
\mbox{}\verb@JobTypeA 2 JobTypeA 2 JobTypeB 1 JobTypeA 2@\\
\mbox{}\verb@JobTypeA 2 JobTypeH 5 JobTypeH 5 JobTypeA 2@\\
\mbox{}\verb@JobTypeA 2 JobTypeB 1@\\
\mbox{}\verb@@
\end{list}
\vspace{-2ex}
\end{flushleft}
Finally, we can take a look at the output from our programme, where 
we not that the jobs have been filtered properly:

\begin{flushleft} \small \label{part14}
\colorbox{light}{$\langle$output from database example {\footnotesize \hypertarget{10c}{10c}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@UrgentJobs@\\
\mbox{}\verb@@\\
\mbox{}\verb@JobTypeH  5@\\
\mbox{}\verb@JobTypeH  5@\\
\mbox{}\verb@JobTypeH  5@\\
\mbox{}\verb@JobTypeH  5@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@NormalJobs@\\
\mbox{}\verb@@\\
\mbox{}\verb@JobTypeA  2@\\
\mbox{}\verb@JobTypeA  2@\\
\mbox{}\verb@JobTypeA  2@\\
\mbox{}\verb@JobTypeA  2@\\
\mbox{}\verb@JobTypeB  1@\\
\mbox{}\verb@JobTypeA  2@\\
\mbox{}\verb@JobTypeA  2@\\
\mbox{}\verb@JobTypeA  2@\\
\mbox{}\verb@JobTypeA  2@\\
\mbox{}\verb@JobTypeB  1@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Not used.
\end{list}
\end{flushleft}
\subsection{The Sporting Goods Store Example}
\label{sec-sports-store-example}

We now look at a simple example of more robust filtering using the 
\code{router} class: suppose we own a sporting goods store ``Bob's 
Big Bad Sports Store'' and we want to send a mailing to customers 
telling them of the sale that is currently being held at the store. 
We have a database of the customers and their past purchases and want 
to send a \emph{single} mailing to each customer to try and encourage 
him or her to come into the store and to make a purchase. Here is an 
overview of our code:

\begin{flushleft} \small \label{part15}
\verb@"sports-store.cpp"@ {\footnotesize \hypertarget{11a}{11a} }$\equiv$
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@#include <algorithm>@\\
\mbox{}\verb@#include <iostream>@\\
\mbox{}\verb@#include <set>@\\
\mbox{}\verb@#include <string>@\\
\mbox{}\verb@#include <vector>@\\
\mbox{}\verb@@\\
\mbox{}\verb@#include "router.hpp"@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\hbox{\colorbox{light}{$\langle$define customer record {\footnotesize \hyperlink{11b}{11b}}$\rangle$}}\verb@@\\
\mbox{}\verb@@\hbox{\colorbox{light}{$\langle$define sales offer destination {\footnotesize \hyperlink{12b}{12b}}$\rangle$}}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@int main()@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  std::vector<customer> store_database;@\\
\mbox{}\verb@  @\hbox{\colorbox{light}{$\langle$create the groups of items for each sport {\footnotesize \hyperlink{14a}{14a}}$\rangle$}}\verb@@\\
\mbox{}\verb@  @\hbox{\colorbox{light}{$\langle$create the customers {\footnotesize \hyperlink{14b}{14b}}$\rangle$}}\verb@@\\
\mbox{}\verb@  @\hbox{\colorbox{light}{$\langle$set up purchases for each customer {\footnotesize \hyperlink{14c}{14c}}$\rangle$}}\verb@@\\
\mbox{}\verb@  @\hbox{\colorbox{light}{$\langle$add each customer to the store database {\footnotesize \hyperlink{15a}{15a}}$\rangle$}}\verb@@\\
\mbox{}\verb@  @\hbox{\colorbox{light}{$\langle$set up the sales items offers {\footnotesize \hyperlink{15b}{15b}}$\rangle$}}\verb@@\\
\mbox{}\verb@  @\hbox{\colorbox{light}{$\langle$create the junk-mailer {\footnotesize \hyperlink{15c}{15c}}$\rangle$}}\verb@@\\
\mbox{}\verb@  @\hbox{\colorbox{light}{$\langle$let the junk-mail begin {\footnotesize \hyperlink{16a}{16a}}$\rangle$}}\verb@@\\
\mbox{}\verb@  return EXIT_SUCCESS;@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@
\end{list}
\vspace{-2ex}
\end{flushleft}
We define a record for a \code{customer}: we need to store the 
customer's name, his or her address, and the items that he or she has 
purchased from our store.

\begin{flushleft} \small
\begin{minipage}{\linewidth}\color{blue} \label{part16}
\colorbox{light}{$\langle$define customer record {\footnotesize \hypertarget{11b}{11b}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@struct customer@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  @\hbox{\colorbox{light}{$\langle$define customer constructor {\footnotesize \hyperlink{12a}{12a}}$\rangle$}}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@  std::string name, address_line_1, address_line_2;@\\
\mbox{}\verb@  std::set<std::string> items_purchased;@\\
\mbox{}\verb@};@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Used in part \hyperlink{11a}{11a}.
\end{list}
\end{minipage}\\[4ex]
\end{flushleft}
Every \code{customer} must have a name and an address; hence we force 
values to be set for each of these fields in our \code{customer} 
constructor.

\begin{flushleft} \small
\begin{minipage}{\linewidth}\color{blue} \label{part17}
\colorbox{light}{$\langle$define customer constructor {\footnotesize \hypertarget{12a}{12a}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@customer(const std::string &new_name,@\\
\mbox{}\verb@           const std::string &new_address_line_1,@\\
\mbox{}\verb@           const std::string &new_address_line_2)@\\
\mbox{}\verb@:name(new_name), address_line_1(new_address_line_1),@\\
\mbox{}\verb@ address_line_2(new_address_line_2)@\\
\mbox{}\verb@{}@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Used in part \hyperlink{11b}{11b}.
\end{list}
\end{minipage}\\[4ex]
\end{flushleft}
What do we need to determine if a user should get a specific mailing? 
Well, we are going to base advertising on past purchases: if a 
customer has purchased basketball equipment in the past then he or 
she will receive an advertisement for basketball equipment now! Our 
predicate must keep track of what is on sale, what items are from the 
same sport, and where to output the advertisement letter (e.g. to 
some sort of file that will be routed to a printer where the junk 
mail will be printed, addressed, and mailed).

\begin{flushleft} \small
\begin{minipage}{\linewidth}\color{blue} \label{part18}
\colorbox{light}{$\langle$define sales offer destination {\footnotesize \hypertarget{12b}{12b}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@template <typename OutputStream>@\\
\mbox{}\verb@class sale_offer : public gdfa::destination<customer>@\\
\mbox{}\verb@{@\\
\mbox{}\verb@public:@\\
\mbox{}\verb@  @\hbox{\colorbox{light}{$\langle$sales\_offer constructor {\footnotesize \hyperlink{12c}{12c}}$\rangle$}}\verb@@\\
\mbox{}\verb@  @\hbox{\colorbox{light}{$\langle$sales\_offer distribute function {\footnotesize \hyperlink{13}{13}}$\rangle$}}\verb@@\\
\mbox{}\verb@private:@\\
\mbox{}\verb@  std::set<std::string> items;@\\
\mbox{}\verb@  std::string item_on_sale;@\\
\mbox{}\verb@  OutputStream &where;@\\
\mbox{}\verb@};@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Used in part \hyperlink{11a}{11a}.
\end{list}
\end{minipage}\\[4ex]
\end{flushleft}
The constructor for the group of items pertaining to a particular 
sport takes an \code{OutputStream} indicating the destination for the 
propaganda letters, two \code{InputIterator}s which are assumed to 
refer to a range of \code{string}s that specify the paraphernalia 
related to that sport, and a \code{std::string} indicating the item 
on sale.

\begin{flushleft} \small
\begin{minipage}{\linewidth}\color{blue} \label{part19}
\colorbox{light}{$\langle$sales\_offer constructor {\footnotesize \hypertarget{12c}{12c}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@template <typename InputIterator>@\\
\mbox{}\verb@sale_offer(OutputStream &new_where, std::string new_item_on_sale,@\\
\mbox{}\verb@           InputIterator first, InputIterator last)@\\
\mbox{}\verb@:where(new_where), item_on_sale(new_item_on_sale),@\\
\mbox{}\verb@ items(first, last)@\\
\mbox{}\verb@{}@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Used in part \hyperlink{12b}{12b}.
\end{list}
\end{minipage}\\[4ex]
\end{flushleft}
Here we do the main work of the \code{purchased\_type}'s filtering: 
see if the customer is a ``fan'' of the given sport by checking to 
see if the customer has purchased any paraphernalia relating to the 
current sport. If so, we print out the letter and return \code{true} 
to indicate that an advertisement has been sent to this customer; 
hence, another advert will \emph{not} be sent to that customer.

\begin{flushleft} \small
\begin{minipage}{\linewidth}\color{blue} \label{part20}
\colorbox{light}{$\langle$sales\_offer distribute function {\footnotesize \hypertarget{13}{13}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@bool distribute(const customer& recipient)@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  std::vector<std::string> items_of_type_purchased;@\\
\mbox{}\verb@  std::set_intersection(recipient.items_purchased.begin(),@\\
\mbox{}\verb@                        recipient.items_purchased.end(),@\\
\mbox{}\verb@                        items.begin(), items.end(),@\\
\mbox{}\verb@                        std::back_inserter(@\\
\mbox{}\verb@                         items_of_type_purchased));@\\
\mbox{}\verb@  if(!items_of_type_purchased.empty())@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    where<<"Bob's Big Bad Sports Store"<<std::endl;@\\
\mbox{}\verb@    where<<"112 42nd St."<<std::endl;@\\
\mbox{}\verb@    where<<"Troy, NY 12180\n\n\n\n"<<std::endl;@\\
\mbox{}\verb@    where<<recipient.name<<std::endl;@\\
\mbox{}\verb@    where<<recipient.address_line_1<<std::endl;@\\
\mbox{}\verb@    where<<recipient.address_line_2<<'\n'<<std::endl;@\\
\mbox{}\verb@    where<<"Dear "<<recipient.name<<":\n"<<std::endl;@\\
\mbox{}\verb@    where<<"Bob's Big Bad Sports Store is pleased to ";@\\
\mbox{}\verb@    where<<"announce that we currently are running a ";@\\
\mbox{}\verb@    where<<"sale on "<<item_on_sale;@\\
\mbox{}\verb@    where<<"s. Since you have purchased items such as ";@\\
\mbox{}\verb@    std::copy(items_of_type_purchased.begin(),@\\
\mbox{}\verb@              items_of_type_purchased.end(),@\\
\mbox{}\verb@              std::ostream_iterator<std::string>(where, ", "));@\\
\mbox{}\verb@    where<<"we think you would be interested in this ";@\\
\mbox{}\verb@    where<<"fantastic promotion. Please visit our store today ";@\\
\mbox{}\verb@    where<<"to take advantage of this limited-time offer!\n";@\\
\mbox{}\verb@    where<<std::endl;@\\
\mbox{}\verb@    where<<"Yours sincerely,\n"<<std::endl;@\\
\mbox{}\verb@    where<<"Big Bob"<<std::endl;@\\
\mbox{}\verb@    return true;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  return false;@\\
\mbox{}\verb@}@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Used in part \hyperlink{12b}{12b}.
\end{list}
\end{minipage}\\[4ex]
\end{flushleft}
Now, we return our attention to our main programme. We need to define 
a database of the things that Bob's sells. These are the goods sold 
at Big Bob's, categorised by the sport to which they pertain:

\begin{flushleft} \small
\begin{minipage}{\linewidth}\color{blue} \label{part21}
\colorbox{light}{$\langle$create the groups of items for each sport {\footnotesize \hypertarget{14a}{14a}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@char *golf_stuff[]={"golf bag", "set of clubs", "titanium driver",@\\
\mbox{}\verb@                      "9-iron"};@\\
\mbox{}\verb@char *lacrosse_stuff[]={"lacrosse stick", "gloves", "helmet"};@\\
\mbox{}\verb@char *basketball_stuff[]={"basketball", "basketball shoes",@\\
\mbox{}\verb@                          "hoop"};@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Used in part \hyperlink{11a}{11a}.
\end{list}
\end{minipage}\\[4ex]
\end{flushleft}
We create a mailing address for each customer.

\begin{flushleft} \small
\begin{minipage}{\linewidth}\color{blue} \label{part22}
\colorbox{light}{$\langle$create the customers {\footnotesize \hypertarget{14b}{14b}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@customer mr_jones("Mr. Charles Jones", "123 Harcourt Terrace",@\\
\mbox{}\verb@                    "Troy, NY 12180");@\\
\mbox{}\verb@customer mrs_hobbins("Mrs. Bobby Hobbins", "56 N. Madison Ave.",@\\
\mbox{}\verb@                     "Chicago, IL 60601");@\\
\mbox{}\verb@customer ms_smith("Ms. Katie Smith", "41 Piedmont Rd. NE",@\\
\mbox{}\verb@                  "Atlanta, GA 3035");@\\
\mbox{}\verb@customer mr_jasper("Mr. George Jasper", "20 Bonneville",@\\
\mbox{}\verb@                   "Las Vegas, NV 89101");@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Used in part \hyperlink{11a}{11a}.
\end{list}
\end{minipage}\\[4ex]
\end{flushleft}
Next, we need to set up the purchase history for each customer. We do 
so by assigning a set of items purchased to the record of each 
customer.

\begin{flushleft} \small
\begin{minipage}{\linewidth}\color{blue} \label{part23}
\colorbox{light}{$\langle$set up purchases for each customer {\footnotesize \hypertarget{14c}{14c}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@char *_mr_jones_purchases[]={"golf bag", "basketball",@\\
\mbox{}\verb@                             "set of clubs"};@\\
\mbox{}\verb@char *_mrs_hobbins_purchases[]={"gloves"};@\\
\mbox{}\verb@char *_ms_smith_purchases[]={"basketball", "basketball shoes"};@\\
\mbox{}\verb@char *_mr_jasper_purchases[]={"9-iron", "lacrosse stick", "hoop"};@\\
\mbox{}\verb@mr_jones.items_purchased=std::set<std::string>(@\\
\mbox{}\verb@ &_mr_jones_purchases[0],@\\
\mbox{}\verb@ &_mr_jones_purchases[sizeof(_mr_jones_purchases)/sizeof(char*)]);@\\
\mbox{}\verb@mrs_hobbins.items_purchased=std::set<std::string>(@\\
\mbox{}\verb@ &_mrs_hobbins_purchases[0],@\\
\mbox{}\verb@ &_mrs_hobbins_purchases[@\\
\mbox{}\verb@  sizeof(_mrs_hobbins_purchases)/sizeof(char*)]);@\\
\mbox{}\verb@ms_smith.items_purchased=std::set<std::string>(@\\
\mbox{}\verb@ &_ms_smith_purchases[0],@\\
\mbox{}\verb@ &_ms_smith_purchases[sizeof(_ms_smith_purchases)/sizeof(char*)]);@\\
\mbox{}\verb@mr_jasper.items_purchased=std::set<std::string>(@\\
\mbox{}\verb@ &_mr_jasper_purchases[0],@\\
\mbox{}\verb@ &_mr_jasper_purchases[sizeof(_mr_jasper_purchases)/@\\
\mbox{}\verb@                       sizeof(char*)]);@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Used in part \hyperlink{11a}{11a}.
\end{list}
\end{minipage}\\[4ex]
\end{flushleft}
The customers need to be inserted into the store database.

\begin{flushleft} \small
\begin{minipage}{\linewidth}\color{blue} \label{part24}
\colorbox{light}{$\langle$add each customer to the store database {\footnotesize \hypertarget{15a}{15a}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@store_database.push_back(mr_jones);@\\
\mbox{}\verb@store_database.push_back(mrs_hobbins);@\\
\mbox{}\verb@store_database.push_back(ms_smith);@\\
\mbox{}\verb@store_database.push_back(mr_jasper);@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Used in part \hyperlink{11a}{11a}.
\end{list}
\end{minipage}\\[4ex]
\end{flushleft}
Next, we set up the advertisements for each sport. For simplicity, we 
dump all of the letters-to-customers to \code{std::cout}. The second 
parameter in each of the constructor calls indicates the name of the 
item that is on sale; the final two parameters indicate the items 
which relate to the same sport as the one on sale.

\begin{flushleft} \small
\begin{minipage}{\linewidth}\color{blue} \label{part25}
\colorbox{light}{$\langle$set up the sales items offers {\footnotesize \hypertarget{15b}{15b}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@sale_offer<std::ostream> golf_sale(std::cout, "titanium driver",@\\
\mbox{}\verb@                                   &golf_stuff[0],@\\
\mbox{}\verb@                                   &golf_stuff[sizeof(golf_stuff)@\\
\mbox{}\verb@                                    /sizeof(char*)]);@\\
\mbox{}\verb@sale_offer<std::ostream> lacrosse_sale(std::cout, "lacrosse stick",@\\
\mbox{}\verb@                                       &lacrosse_stuff[0],@\\
\mbox{}\verb@                                       &lacrosse_stuff[@\\
\mbox{}\verb@                                        sizeof(lacrosse_stuff)@\\
\mbox{}\verb@                                        /sizeof(char*)]);@\\
\mbox{}\verb@sale_offer<std::ostream> basketball_sale(std::cout, "hoop",@\\
\mbox{}\verb@                                         &basketball_stuff[0],@\\
\mbox{}\verb@                                         &basketball_stuff[@\\
\mbox{}\verb@                                          sizeof(basketball_stuff)@\\
\mbox{}\verb@                                          /sizeof(char*)]);@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Used in part \hyperlink{11a}{11a}.
\end{list}
\end{minipage}\\[4ex]
\end{flushleft}
Add each of the sale adverts to the junk mailer. Since golf equipment 
is more expensive than lacrosse equipment which, in turn, is more 
expensive than basketball equipment, we prioritise the advertisements 
appropriately: if a customer has purchased both golf and lacrosse 
equipment, we want to send him or her the golf advertisement and 
\emph{not} the lacrosse advertisement since we, at Big Bob's, are 
trying to make the most money off of the customers and we can best do 
so by advertising expensive products to them.

\begin{flushleft} \small
\begin{minipage}{\linewidth}\color{blue} \label{part26}
\colorbox{light}{$\langle$create the junk-mailer {\footnotesize \hypertarget{15c}{15c}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@typedef gdfa::router<customer> mailer;@\\
\mbox{}\verb@mailer junk_mailer;@\\
\mbox{}\verb@junk_mailer.add_destination(golf_sale,@\\
\mbox{}\verb@ gdfa::router<customer>::high_priority);@\\
\mbox{}\verb@junk_mailer.add_destination(lacrosse_sale);@\\
\mbox{}\verb@junk_mailer.add_destination(basketball_sale,@\\
\mbox{}\verb@ gdfa::router<customer>::low_priority);@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Used in part \hyperlink{11a}{11a}.
\end{list}
\end{minipage}\\[4ex]
\end{flushleft}
Finally, we produce the items to-be-mailed using the junk-mailer that 
we have created and the store's database: we pass the database to the 
mailer and the mailer determines the most expensive sale item which 
fits the tastes of each customer and then creates a proper mailing 
for that advertisement, addressed to the customer and making mention 
of the previously-purchased products for that sport.

\begin{flushleft} \small
\begin{minipage}{\linewidth}\color{blue} \label{part27}
\colorbox{light}{$\langle$let the junk-mail begin {\footnotesize \hypertarget{16a}{16a}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@junk_mailer.distribute(store_database.begin(),@\\
\mbox{}\verb@                         store_database.end());@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Used in part \hyperlink{11a}{11a}.
\end{list}
\end{minipage}\\[4ex]
\end{flushleft}
In the interest of space, we present here one of the advertisements 
rather than all of them, but this should give a reasonable idea of 
the style of the output:\footnote{Line breaks were added to the 
output so as to make it readable.}

\begin{flushleft} \small \label{part28}
\colorbox{light}{$\langle$sample of output from sporting store example {\footnotesize \hypertarget{16b}{16b}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@Bob's Big Bad Sports Store@\\
\mbox{}\verb@112 42nd St.@\\
\mbox{}\verb@Troy, NY 12180@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@Mr. Charles Jones@\\
\mbox{}\verb@123 Harcourt Terrace@\\
\mbox{}\verb@Troy, NY 12180@\\
\mbox{}\verb@@\\
\mbox{}\verb@Dear Mr. Charles Jones:@\\
\mbox{}\verb@@\\
\mbox{}\verb@Bob's Big Bad Sports Store is pleased to announce that we currently@\\
\mbox{}\verb@are running a sale on titanium drivers. Since you have purchased@\\
\mbox{}\verb@items such as golf bag, set of clubs, we think you would be@\\
\mbox{}\verb@interested in this fantastic promotion. Please visit our store@\\
\mbox{}\verb@today to take advantage of this limited-time offer!@\\
\mbox{}\verb@@\\
\mbox{}\verb@Yours sincerely,@\\
\mbox{}\verb@@\\
\mbox{}\verb@Big Bob@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Not used.
\end{list}
\end{flushleft}
\subsection{The Criminal Profiling Example}
\label{sec-criminal-example}
We now look at a slightly more complicated use of the \code{router} 
class. Suppose that we know that two suspects were spotted by 
eyewitnesses leaving a crime scene matching the following 
descriptions: Suspect 1 is between 1.65 and 1.75m tall, weighs 
between 65 and 75kg, and has brown hair; Suspect 2 is between 1.75 
and 1.85m tall, weights between 80 and 90kg and also has brown hair. 
Given that we have a database of criminals, we want to find out if 
any criminals in the database match these descriptions so that we can 
round up the usual suspects and interrogate them. The purpose of this 
programme is to illustrate a multi-tier use of the \code{router} 
class: we will first filter based on height, next filter based on 
weight, and, finally, filter based on hair-colour in a three-step 
process. This example is, of course, very contrived, but this could 
be used for advanced data-mining or analysis of complex data in a 
real programme.

\begin{flushleft} \small \label{part29}
\verb@"criminal.cpp"@ {\footnotesize \hypertarget{17}{17} }$\equiv$
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@#include <algorithm>@\\
\mbox{}\verb@#include <iostream>@\\
\mbox{}\verb@#include <map>@\\
\mbox{}\verb@#include <string>@\\
\mbox{}\verb@#include <vector>@\\
\mbox{}\verb@@\\
\mbox{}\verb@#include "router.hpp"@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\hbox{\colorbox{light}{$\langle$define criminal profile {\footnotesize \hyperlink{18a}{18a}}$\rangle$}}\verb@@\\
\mbox{}\verb@@\hbox{\colorbox{light}{$\langle$define classes for filtering {\footnotesize \hyperlink{20b}{20b}}$\rangle$}}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@int main()@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  std::vector<criminal> criminal_database;@\\
\mbox{}\verb@  std::vector<criminal> suspect1, suspect2;@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  @\hbox{\colorbox{light}{$\langle$create the criminal records {\footnotesize \hyperlink{24}{24}}$\rangle$}}\verb@@\\
\mbox{}\verb@  @\hbox{\colorbox{light}{$\langle$run the search {\footnotesize \hyperlink{25a}{25a}}$\rangle$}}\verb@@\\
\mbox{}\verb@  @\hbox{\colorbox{light}{$\langle$display the results {\footnotesize \hyperlink{27c}{27c}}$\rangle$}}\verb@@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  return EXIT_SUCCESS;@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@
\end{list}
\vspace{-2ex}
\end{flushleft}
Since we need a way to store a criminal's profile, we create a 
structure in which we can store vital information such as name, 
height, weight, build, hair-colour, eye-colour, sex, and race.

\begin{flushleft} \small
\begin{minipage}{\linewidth}\color{blue} \label{part30}
\colorbox{light}{$\langle$define criminal profile {\footnotesize \hypertarget{18a}{18a}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@struct criminal@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  @\hbox{\colorbox{light}{$\langle$define useful enumerations for criminal data {\footnotesize \hyperlink{18b}{18b}}$\rangle$}}\verb@@\\
\mbox{}\verb@  @\hbox{\colorbox{light}{$\langle$criminal constructor {\footnotesize \hyperlink{18c}{18c}}$\rangle$}}\verb@@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  std::string name;@\\
\mbox{}\verb@  double height;@\\
\mbox{}\verb@  unsigned int weight;@\\
\mbox{}\verb@  build my_build;@\\
\mbox{}\verb@  hair_colour my_hair_colour;@\\
\mbox{}\verb@  eye_colour my_eye_colour;@\\
\mbox{}\verb@  sex my_sex;@\\
\mbox{}\verb@  race my_race;@\\
\mbox{}\verb@};@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\hbox{\colorbox{light}{$\langle$criminal output operator {\footnotesize \hyperlink{19}{19}}$\rangle$}}\verb@@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Used in part \hyperlink{17}{17}.
\end{list}
\end{minipage}\\[4ex]
\end{flushleft}
A few useful enumerations are needed to help us deal with the data in 
an abstract sense. \code{``\_hair''} is suffixed on each of the 
hair-colours because of conflicts that would otherwise arise between 
the constants in the \code{hair\_colour} enumeration and the 
\code{eye\_colour} and \code{race} enumerations.

\begin{flushleft} \small
\begin{minipage}{\linewidth}\color{blue} \label{part31}
\colorbox{light}{$\langle$define useful enumerations for criminal data {\footnotesize \hypertarget{18b}{18b}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@enum build {thin, medium, stocky, heavy};@\\
\mbox{}\verb@enum hair_colour {black_hair, brown_hair, blonde_hair, white_hair,@\\
\mbox{}\verb@                  red_hair, grey_hair};@\\
\mbox{}\verb@enum eye_colour {brown, blue, green, hazel};@\\
\mbox{}\verb@enum sex {male, female};@\\
\mbox{}\verb@enum race {black, white, hispanic, arab};@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Used in part \hyperlink{18a}{18a}.
\end{list}
\end{minipage}\\[4ex]
\end{flushleft}
The constructor simply initialises the right values.

\begin{flushleft} \small
\begin{minipage}{\linewidth}\color{blue} \label{part32}
\colorbox{light}{$\langle$criminal constructor {\footnotesize \hypertarget{18c}{18c}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@criminal(const std::string &new_name, double new_height,@\\
\mbox{}\verb@         unsigned int new_weight, build new_build,@\\
\mbox{}\verb@         hair_colour new_hair_colour,@\\
\mbox{}\verb@         eye_colour new_eye_colour, sex new_sex,@\\
\mbox{}\verb@         race new_race)@\\
\mbox{}\verb@:name(new_name), height(new_height), weight(new_weight),@\\
\mbox{}\verb@ my_build(new_build), my_hair_colour(new_hair_colour),@\\
\mbox{}\verb@ my_eye_colour(new_eye_colour), my_sex(new_sex), my_race(new_race)@\\
\mbox{}\verb@{}@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Used in part \hyperlink{18a}{18a}.
\end{list}
\end{minipage}\\[4ex]
\end{flushleft}
It would be nice to have a convenient way to display a criminal's 
statistics; pursuant to this goal, we create an output operator for a 
\code{criminal} object.

\begin{flushleft} \small
\begin{minipage}{\linewidth}\color{blue} \label{part33}
\colorbox{light}{$\langle$criminal output operator {\footnotesize \hypertarget{19}{19}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@std::ostream& operator<<(std::ostream &out,@\\
\mbox{}\verb@                           const criminal &to_print)@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  @\hbox{\colorbox{light}{$\langle$create string mappings for the enumerations {\footnotesize \hyperlink{20a}{20a}}$\rangle$}}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@  out<<to_print.name<<std::endl;@\\
\mbox{}\verb@  out<<"  height: "<<to_print.height<<'m'<<std::endl;@\\
\mbox{}\verb@  out<<"  weight: "<<to_print.weight<<"kg"<<std::endl;@\\
\mbox{}\verb@  out<<"  build : "<<build_labels[to_print.my_build]<<std::endl;@\\
\mbox{}\verb@  out<<"  hair  : "<<hair_labels[to_print.my_hair_colour];@\\
\mbox{}\verb@  out<<std::endl;@\\
\mbox{}\verb@  out<<"  eyes  : "<<eye_labels[to_print.my_eye_colour]<<std::endl;@\\
\mbox{}\verb@  out<<"  sex   : "<<sex_labels[to_print.my_sex]<<std::endl;@\\
\mbox{}\verb@  out<<"  race  : "<<race_labels[to_print.my_race]<<std::endl;@\\
\mbox{}\verb@}@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Used in part \hyperlink{18a}{18a}.
\end{list}
\end{minipage}\\[4ex]
\end{flushleft}
For convenience during printing, we create a group of mappings of 
\code{std::string} labels for the enumerated types. The map is only 
initialised on the first time that the output operator is called.

\begin{flushleft} \small
\begin{minipage}{\linewidth}\color{blue} \label{part34}
\colorbox{light}{$\langle$create string mappings for the enumerations {\footnotesize \hypertarget{20a}{20a}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@static bool first=true;@\\
\mbox{}\verb@@\\
\mbox{}\verb@static std::map<criminal::build, std::string> build_labels;@\\
\mbox{}\verb@static std::map<criminal::hair_colour, std::string> hair_labels;@\\
\mbox{}\verb@static std::map<criminal::eye_colour, std::string> eye_labels;@\\
\mbox{}\verb@static std::map<criminal::sex, std::string> sex_labels;@\\
\mbox{}\verb@static std::map<criminal::race, std::string> race_labels;@\\
\mbox{}\verb@@\\
\mbox{}\verb@if(first)@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  build_labels[criminal::thin]="thin";@\\
\mbox{}\verb@  build_labels[criminal::medium]="medium";@\\
\mbox{}\verb@  build_labels[criminal::stocky]="stocky";@\\
\mbox{}\verb@  build_labels[criminal::heavy]="heavy";@\\
\mbox{}\verb@@\\
\mbox{}\verb@  hair_labels[criminal::black_hair]="black";@\\
\mbox{}\verb@  hair_labels[criminal::brown_hair]="brown";@\\
\mbox{}\verb@  hair_labels[criminal::blonde_hair]="blonde";@\\
\mbox{}\verb@  hair_labels[criminal::white_hair]="white";@\\
\mbox{}\verb@  hair_labels[criminal::red_hair]="red";@\\
\mbox{}\verb@  hair_labels[criminal::grey_hair]="grey";@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  eye_labels[criminal::brown]="brown";@\\
\mbox{}\verb@  eye_labels[criminal::blue]="blue";@\\
\mbox{}\verb@  eye_labels[criminal::green]="green";@\\
\mbox{}\verb@  eye_labels[criminal::hazel]="hazel";@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  sex_labels[criminal::male]="male";@\\
\mbox{}\verb@  sex_labels[criminal::female]="female";@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  race_labels[criminal::black]="black";@\\
\mbox{}\verb@  race_labels[criminal::white]="white";@\\
\mbox{}\verb@  race_labels[criminal::hispanic]="hispanic";@\\
\mbox{}\verb@  race_labels[criminal::arab]="arab";@\\
\mbox{}\verb@@\\
\mbox{}\verb@  first=false;@\\
\mbox{}\verb@}@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Used in part \hyperlink{19}{19}.
\end{list}
\end{minipage}\\[4ex]
\end{flushleft}
Next, we create several ways of filtering criminals.

\begin{flushleft} \small
\begin{minipage}{\linewidth}\color{blue} \label{part35}
\colorbox{light}{$\langle$define classes for filtering {\footnotesize \hypertarget{20b}{20b}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@@\hbox{\colorbox{light}{$\langle$filter by height {\footnotesize \hyperlink{21a}{21a}}$\rangle$}}\verb@@\\
\mbox{}\verb@@\hbox{\colorbox{light}{$\langle$filter by weight {\footnotesize \hyperlink{22a}{22a}}$\rangle$}}\verb@@\\
\mbox{}\verb@@\hbox{\colorbox{light}{$\langle$filter by hair-colour {\footnotesize \hyperlink{23a}{23a}}$\rangle$}}\verb@@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Used in part \hyperlink{17}{17}.
\end{list}
\end{minipage}\\[4ex]
\end{flushleft}
We need a way to filter the criminals in our database by their 
heights. Since witness testimony is often inaccurate, we want to be 
able to search for an height range. This \code{destination} will 
allow us to do this.

\begin{flushleft} \small
\begin{minipage}{\linewidth}\color{blue} \label{part36}
\colorbox{light}{$\langle$filter by height {\footnotesize \hypertarget{21a}{21a}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@template <typename OutputIterator>@\\
\mbox{}\verb@class height_filter : public gdfa::destination<criminal>@\\
\mbox{}\verb@{@\\
\mbox{}\verb@public:@\\
\mbox{}\verb@  @\hbox{\colorbox{light}{$\langle$height\_filter constructor {\footnotesize \hyperlink{21b}{21b}}$\rangle$}}\verb@@\\
\mbox{}\verb@  @\hbox{\colorbox{light}{$\langle$height\_filter distribute {\footnotesize \hyperlink{21c}{21c}}$\rangle$}}\verb@@\\
\mbox{}\verb@  @\\
\mbox{}\verb@private:@\\
\mbox{}\verb@  double min, max;@\\
\mbox{}\verb@  OutputIterator where;@\\
\mbox{}\verb@};@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Used in part \hyperlink{20b}{20b}.
\end{list}
\end{minipage}\\[4ex]
\end{flushleft}
The constructor just takes an \code{OutputIterator} and two 
\code{double}s which define the range of height values that we seek.

\begin{flushleft} \small
\begin{minipage}{\linewidth}\color{blue} \label{part37}
\colorbox{light}{$\langle$height\_filter constructor {\footnotesize \hypertarget{21b}{21b}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@height_filter(OutputIterator new_where, double new_min,@\\
\mbox{}\verb@              double new_max)@\\
\mbox{}\verb@:where(new_where), min(new_min), max(new_max)@\\
\mbox{}\verb@{}@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Used in part \hyperlink{21a}{21a}.
\end{list}
\end{minipage}\\[4ex]
\end{flushleft}
Next, we compare a criminal's height against the range that we are 
looking for; output his or her information if an height match is 
found. \code{false} is vacuously returned because a criminal may 
match the description of one or more suspects.

\begin{flushleft} \small
\begin{minipage}{\linewidth}\color{blue} \label{part38}
\colorbox{light}{$\langle$height\_filter distribute {\footnotesize \hypertarget{21c}{21c}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@bool distribute(const criminal &suspect)@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  if(min<=suspect.height && suspect.height<=max)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    *(where++)=suspect;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  return false;@\\
\mbox{}\verb@}@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Used in part \hyperlink{21a}{21a}.
\end{list}
\end{minipage}\\[4ex]
\end{flushleft}
We also want to be able to filter by weight. We need a separate 
\code{weight\_filter} class because in the \code{distribute} 
function, we need to access different members of the \code{criminal} 
structure.

\begin{flushleft} \small
\begin{minipage}{\linewidth}\color{blue} \label{part39}
\colorbox{light}{$\langle$filter by weight {\footnotesize \hypertarget{22a}{22a}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@template <typename OutputIterator>@\\
\mbox{}\verb@class weight_filter : public gdfa::destination<criminal>@\\
\mbox{}\verb@{@\\
\mbox{}\verb@public:@\\
\mbox{}\verb@  @\hbox{\colorbox{light}{$\langle$weight\_filter constructor {\footnotesize \hyperlink{22b}{22b}}$\rangle$}}\verb@@\\
\mbox{}\verb@  @\hbox{\colorbox{light}{$\langle$weight\_filter distribute {\footnotesize \hyperlink{22c}{22c}}$\rangle$}}\verb@@\\
\mbox{}\verb@    @\\
\mbox{}\verb@private:@\\
\mbox{}\verb@  unsigned int min, max;@\\
\mbox{}\verb@  OutputIterator where;@\\
\mbox{}\verb@};@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Used in part \hyperlink{20b}{20b}.
\end{list}
\end{minipage}\\[4ex]
\end{flushleft}
We create another trivial constructor.

\begin{flushleft} \small
\begin{minipage}{\linewidth}\color{blue} \label{part40}
\colorbox{light}{$\langle$weight\_filter constructor {\footnotesize \hypertarget{22b}{22b}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@weight_filter(OutputIterator new_where, unsigned int new_min,@\\
\mbox{}\verb@              unsigned int new_max)@\\
\mbox{}\verb@:where(new_where), min(new_min), max(new_max)@\\
\mbox{}\verb@{}@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Used in part \hyperlink{22a}{22a}.
\end{list}
\end{minipage}\\[4ex]
\end{flushleft}
We distribute exactly like we did for \code{filter\_height} except 
that we change \code{suspect.height} to \code{suspect.weight}.

\begin{flushleft} \small
\begin{minipage}{\linewidth}\color{blue} \label{part41}
\colorbox{light}{$\langle$weight\_filter distribute {\footnotesize \hypertarget{22c}{22c}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@bool distribute(const criminal &suspect)@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  if(min<=suspect.weight && suspect.weight<=max)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    *(where++)=suspect;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  return true;@\\
\mbox{}\verb@}@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Used in part \hyperlink{22a}{22a}.
\end{list}
\end{minipage}\\[4ex]
\end{flushleft}
Since we also have information about the suspects' hair-colour, we 
create a \code{destination} to filter by hair-colour.

\begin{flushleft} \small
\begin{minipage}{\linewidth}\color{blue} \label{part42}
\colorbox{light}{$\langle$filter by hair-colour {\footnotesize \hypertarget{23a}{23a}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@template <typename OutputIterator>@\\
\mbox{}\verb@class colour_filter : public gdfa::destination<criminal>@\\
\mbox{}\verb@{@\\
\mbox{}\verb@public:@\\
\mbox{}\verb@  typedef criminal::hair_colour colour;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  @\hbox{\colorbox{light}{$\langle$colour\_filter constructor {\footnotesize \hyperlink{23b}{23b}}$\rangle$}}\verb@@\\
\mbox{}\verb@  @\hbox{\colorbox{light}{$\langle$colour\_filter distribute {\footnotesize \hyperlink{23c}{23c}}$\rangle$}}\verb@@\\
\mbox{}\verb@    @\\
\mbox{}\verb@private:@\\
\mbox{}\verb@  colour to_match;@\\
\mbox{}\verb@  OutputIterator where;@\\
\mbox{}\verb@};@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Used in part \hyperlink{20b}{20b}.
\end{list}
\end{minipage}\\[4ex]
\end{flushleft}
Yet another fairly simple constructor.

\begin{flushleft} \small
\begin{minipage}{\linewidth}\color{blue} \label{part43}
\colorbox{light}{$\langle$colour\_filter constructor {\footnotesize \hypertarget{23b}{23b}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@colour_filter(OutputIterator new_where, colour new_to_match)@\\
\mbox{}\verb@:where(new_where), to_match(new_to_match)@\\
\mbox{}\verb@{}@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Used in part \hyperlink{23a}{23a}.
\end{list}
\end{minipage}\\[4ex]
\end{flushleft}
Use a simple equality comparison against a known hair-colour and the 
criminal's to see if he or she matches the suspect's description.

\begin{flushleft} \small
\begin{minipage}{\linewidth}\color{blue} \label{part44}
\colorbox{light}{$\langle$colour\_filter distribute {\footnotesize \hypertarget{23c}{23c}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@bool distribute(const criminal &suspect)@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  if(suspect.my_hair_colour==to_match)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    *(where++)=suspect;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  return true;@\\
\mbox{}\verb@}@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Used in part \hyperlink{23a}{23a}.
\end{list}
\end{minipage}\\[4ex]
\end{flushleft}
We look again at the main programme. The database is populated with a 
set of criminals,\footnote{This information is pulled from the U.S. 
FBI's Most-Wanted database; this example is not intended to indicate 
the authors' support of profiling in investigations.} each created 
using the \code{criminal} constructor.

\begin{flushleft} \small
\begin{minipage}{\linewidth}\color{blue} \label{part45}
\colorbox{light}{$\langle$create the criminal records {\footnotesize \hypertarget{24}{24}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@criminal_database.push_back(criminal("Usama Bin Laden",@\\
\mbox{}\verb@                            1.96, 72, criminal::thin,@\\
\mbox{}\verb@                            criminal::brown_hair,@\\
\mbox{}\verb@                            criminal::brown, criminal::male,@\\
\mbox{}\verb@                            criminal::arab));@\\
\mbox{}\verb@criminal_database.push_back(criminal("Hopeton Eric Brown",@\\
\mbox{}\verb@                            1.73, 80, criminal::medium,@\\
\mbox{}\verb@                            criminal::black_hair,@\\
\mbox{}\verb@                            criminal::brown, criminal::male,@\\
\mbox{}\verb@                            criminal::black));@\\
\mbox{}\verb@criminal_database.push_back(criminal("James J. Bulger",@\\
\mbox{}\verb@                            1.73, 70, criminal::medium,@\\
\mbox{}\verb@                            criminal::grey_hair,@\\
\mbox{}\verb@                            criminal::blue, criminal::male,@\\
\mbox{}\verb@                            criminal::white));@\\
\mbox{}\verb@criminal_database.push_back(criminal("Robert William Fisher",@\\
\mbox{}\verb@                            1.83, 86, criminal::medium,@\\
\mbox{}\verb@                            criminal::brown_hair,@\\
\mbox{}\verb@                            criminal::blue, criminal::male,@\\
\mbox{}\verb@                            criminal::white));@\\
\mbox{}\verb@criminal_database.push_back(criminal("Victor Manuel Gerena", @\\
\mbox{}\verb@                            1.68, 75, criminal::stocky, @\\
\mbox{}\verb@                            criminal::brown_hair,@\\
\mbox{}\verb@                            criminal::green, criminal::male,@\\
\mbox{}\verb@                            criminal::hispanic));@\\
\mbox{}\verb@criminal_database.push_back(criminal("Glen Stewart Godwin",@\\
\mbox{}\verb@                            1.83, 90, criminal::medium,@\\
\mbox{}\verb@                            criminal::grey_hair,@\\
\mbox{}\verb@                            criminal::green, criminal::male,@\\
\mbox{}\verb@                            criminal::white));@\\
\mbox{}\verb@criminal_database.push_back(criminal("Richard Steve Goldberg",@\\
\mbox{}\verb@                            1.83, 72, criminal::medium,@\\
\mbox{}\verb@                            criminal::brown_hair,@\\
\mbox{}\verb@                            criminal::brown, criminal::male,@\\
\mbox{}\verb@                            criminal::white));@\\
\mbox{}\verb@criminal_database.push_back(criminal("Eric Robert Rudolph",@\\
\mbox{}\verb@                            1.80, 78, criminal::medium,@\\
\mbox{}\verb@                            criminal::brown_hair,@\\
\mbox{}\verb@                            criminal::blue, criminal::male,@\\
\mbox{}\verb@                            criminal::white));@\\
\mbox{}\verb@criminal_database.push_back(criminal("James Spencer Springette", @\\
\mbox{}\verb@                            1.80, 109, criminal::heavy, @\\
\mbox{}\verb@                            criminal::black_hair,@\\
\mbox{}\verb@                            criminal::brown, criminal::male,@\\
\mbox{}\verb@                            criminal::white));@\\
\mbox{}\verb@criminal_database.push_back(criminal("Donald Eugene Webb",@\\
\mbox{}\verb@                            1.75, 75, criminal::medium,@\\
\mbox{}\verb@                            criminal::grey_hair,@\\
\mbox{}\verb@                            criminal::brown, criminal::male,@\\
\mbox{}\verb@                            criminal::white));@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Used in part \hyperlink{17}{17}.
\end{list}
\end{minipage}\\[4ex]
\end{flushleft}
In an overview of our search, as mentioned earlier, we filter based 
on height, then based on weight, then based on hair-colour.

\begin{flushleft} \small
\begin{minipage}{\linewidth}\color{blue} \label{part46}
\colorbox{light}{$\langle$run the search {\footnotesize \hypertarget{25a}{25a}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@std::vector<criminal> temp1, temp2;@\\
\mbox{}\verb@typedef std::back_insert_iterator<std::vector<criminal> > BItype;@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\hbox{\colorbox{light}{$\langle$filter based on height {\footnotesize \hyperlink{25b}{25b}}$\rangle$}}\verb@@\\
\mbox{}\verb@@\hbox{\colorbox{light}{$\langle$filter based on weight {\footnotesize \hyperlink{26a}{26a}}$\rangle$}}\verb@@\\
\mbox{}\verb@@\hbox{\colorbox{light}{$\langle$filter based on hair-colour {\footnotesize \hyperlink{26d}{26d}}$\rangle$}}\verb@@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Used in part \hyperlink{17}{17}.
\end{list}
\end{minipage}\\[4ex]
\end{flushleft}
First, we separate the criminals in the database based on height.

\begin{flushleft} \small
\begin{minipage}{\linewidth}\color{blue} \label{part47}
\colorbox{light}{$\langle$filter based on height {\footnotesize \hypertarget{25b}{25b}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@@\hbox{\colorbox{light}{$\langle$set up height filters {\footnotesize \hyperlink{25c}{25c}}$\rangle$}}\verb@@\\
\mbox{}\verb@@\hbox{\colorbox{light}{$\langle$run height filter {\footnotesize \hyperlink{25d}{25d}}$\rangle$}}\verb@@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Used in part \hyperlink{25a}{25a}.
\end{list}
\end{minipage}\\[4ex]
\end{flushleft}
We know that one of the suspects is between 1.65 and 1.75m and that 
the other is between 1.75 and 1.85 in height; we create a 
\code{destination} for each (more precisely, a \code{height\_filter}) 
and add these to a \code{router}.

\begin{flushleft} \small
\begin{minipage}{\linewidth}\color{blue} \label{part48}
\colorbox{light}{$\langle$set up height filters {\footnotesize \hypertarget{25c}{25c}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@height_filter<BItype> suspect_1_height(std::back_inserter(@\\
\mbox{}\verb@                                          suspect1),@\\
\mbox{}\verb@                                         1.65, 1.75);@\\
\mbox{}\verb@height_filter<BItype> suspect_2_height(std::back_inserter(@\\
\mbox{}\verb@                                        suspect2),@\\
\mbox{}\verb@                                       1.75, 1.85);@\\
\mbox{}\verb@gdfa::router<criminal> search_by_height;@\\
\mbox{}\verb@search_by_height.add_destination(suspect_1_height);@\\
\mbox{}\verb@search_by_height.add_destination(suspect_2_height);@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Used in part \hyperlink{25b}{25b}.
\end{list}
\end{minipage}\\[4ex]
\end{flushleft}
Then, we distribute the criminals from the database into the vectors 
\code{suspect1} and \code{suspect2}; criminals who fit neither of the 
sets of height requirements are discarded.

\begin{flushleft} \small
\begin{minipage}{\linewidth}\color{blue} \label{part49}
\colorbox{light}{$\langle$run height filter {\footnotesize \hypertarget{25d}{25d}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@search_by_height.distribute(criminal_database.begin(),@\\
\mbox{}\verb@                            criminal_database.end());@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Used in part \hyperlink{25b}{25b}.
\end{list}
\end{minipage}\\[4ex]
\end{flushleft}
Next, we filter based on the weights described by the eyewitnesses.

\begin{flushleft} \small
\begin{minipage}{\linewidth}\color{blue} \label{part50}
\colorbox{light}{$\langle$filter based on weight {\footnotesize \hypertarget{26a}{26a}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@@\hbox{\colorbox{light}{$\langle$set up weight filters {\footnotesize \hyperlink{26b}{26b}}$\rangle$}}\verb@@\\
\mbox{}\verb@@\hbox{\colorbox{light}{$\langle$run weight filters {\footnotesize \hyperlink{26c}{26c}}$\rangle$}}\verb@@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Used in part \hyperlink{25a}{25a}.
\end{list}
\end{minipage}\\[4ex]
\end{flushleft}
We now set a \code{router} for each criminal's weight: 65 to 75kg for 
the first, 80 to 90kg for the second. It would be nice if we could 
use the trivial version of \code{distribute}, but there seems no 
logical location where the criminals whose records did not match the 
predicate would be output. This version does not output them to any 
iterator, which is exactly what is desired.

\begin{flushleft} \small
\begin{minipage}{\linewidth}\color{blue} \label{part51}
\colorbox{light}{$\langle$set up weight filters {\footnotesize \hypertarget{26b}{26b}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@weight_filter<BItype> suspect_1_weight(std::back_inserter(temp1),@\\
\mbox{}\verb@                                       65, 75);@\\
\mbox{}\verb@gdfa::router<criminal> filter_1_by_weight;@\\
\mbox{}\verb@filter_1_by_weight.add_destination(suspect_1_weight);@\\
\mbox{}\verb@@\\
\mbox{}\verb@weight_filter<BItype> suspect_2_weight(std::back_inserter(temp2),@\\
\mbox{}\verb@                                       80, 90);@\\
\mbox{}\verb@gdfa::router<criminal> filter_2_by_weight;@\\
\mbox{}\verb@filter_2_by_weight.add_destination(suspect_2_weight);@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Used in part \hyperlink{26a}{26a}.
\end{list}
\end{minipage}\\[4ex]
\end{flushleft}
Now, filter by weight the criminals who (so far) match the 
description of the respective suspects. The refined suspect lists are 
held in \code{temp1} and \code{temp2} for suspect1 and suspect2, 
respectively, we copy this back into \code{suspect1} and 
\code{suspect2} and clear the temporary \code{std::vector}s.

\begin{flushleft} \small
\begin{minipage}{\linewidth}\color{blue} \label{part52}
\colorbox{light}{$\langle$run weight filters {\footnotesize \hypertarget{26c}{26c}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@filter_1_by_weight.distribute(suspect1.begin(), suspect1.end());@\\
\mbox{}\verb@filter_2_by_weight.distribute(suspect2.begin(), suspect2.end());@\\
\mbox{}\verb@@\\
\mbox{}\verb@suspect1=temp1;@\\
\mbox{}\verb@suspect2=temp2;@\\
\mbox{}\verb@@\\
\mbox{}\verb@temp1.clear();@\\
\mbox{}\verb@temp2.clear();@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Used in part \hyperlink{26a}{26a}.
\end{list}
\end{minipage}\\[4ex]
\end{flushleft}
Finally, we examine the hair-colour entries for each of the criminals 
in our database and eliminate those who do not match.

\begin{flushleft} \small
\begin{minipage}{\linewidth}\color{blue} \label{part53}
\colorbox{light}{$\langle$filter based on hair-colour {\footnotesize \hypertarget{26d}{26d}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@@\hbox{\colorbox{light}{$\langle$set up colour filters {\footnotesize \hyperlink{27a}{27a}}$\rangle$}}\verb@@\\
\mbox{}\verb@@\hbox{\colorbox{light}{$\langle$run colour filters {\footnotesize \hyperlink{27b}{27b}}$\rangle$}}\verb@@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Used in part \hyperlink{25a}{25a}.
\end{list}
\end{minipage}\\[4ex]
\end{flushleft}
We set up a filter for each suspect to eliminate all potential 
suspects that do not have brown hair.

\begin{flushleft} \small
\begin{minipage}{\linewidth}\color{blue} \label{part54}
\colorbox{light}{$\langle$set up colour filters {\footnotesize \hypertarget{27a}{27a}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@colour_filter<BItype> suspect_1_colour(std::back_inserter(temp1),@\\
\mbox{}\verb@                                       criminal::brown_hair);@\\
\mbox{}\verb@gdfa::router<criminal> filter_1_by_colour;@\\
\mbox{}\verb@filter_1_by_colour.add_destination(suspect_1_colour);@\\
\mbox{}\verb@@\\
\mbox{}\verb@colour_filter<BItype> suspect_2_colour(std::back_inserter(temp2),@\\
\mbox{}\verb@                                       criminal::brown_hair);@\\
\mbox{}\verb@gdfa::router<criminal> filter_2_by_colour;@\\
\mbox{}\verb@filter_2_by_colour.add_destination(suspect_2_colour);@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Used in part \hyperlink{26d}{26d}.
\end{list}
\end{minipage}\\[4ex]
\end{flushleft}
Run these filters and copy the results back from the temp 
\code{std::vector}s. We are done at last!

\begin{flushleft} \small
\begin{minipage}{\linewidth}\color{blue} \label{part55}
\colorbox{light}{$\langle$run colour filters {\footnotesize \hypertarget{27b}{27b}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@filter_1_by_colour.distribute(suspect1.begin(), suspect1.end());@\\
\mbox{}\verb@filter_2_by_colour.distribute(suspect2.begin(), suspect2.end());@\\
\mbox{}\verb@@\\
\mbox{}\verb@suspect1=temp1;@\\
\mbox{}\verb@suspect2=temp2;@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Used in part \hyperlink{26d}{26d}.
\end{list}
\end{minipage}\\[4ex]
\end{flushleft}
Calls to \code{std::copy} get the data printed, and, voil\'a, we have 
a list of all criminals matching each of the two suspects described 
by the eyewitnesses who saw them fleeing the scene of the crime.

\begin{flushleft} \small
\begin{minipage}{\linewidth}\color{blue} \label{part56}
\colorbox{light}{$\langle$display the results {\footnotesize \hypertarget{27c}{27c}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@std::cout<<"--- Criminals matching the description ";@\\
\mbox{}\verb@std::cout<<"of Suspect1 ---";@\\
\mbox{}\verb@std::cout<<std::endl;@\\
\mbox{}\verb@std::copy(temp1.begin(), temp1.end(),@\\
\mbox{}\verb@          std::ostream_iterator<criminal>(std::cout, "\n"));@\\
\mbox{}\verb@std::cout<<'\n'<<std::endl;@\\
\mbox{}\verb@@\\
\mbox{}\verb@std::cout<<"--- Criminals matching the description ";@\\
\mbox{}\verb@std::cout<<"of Suspect2 ---";@\\
\mbox{}\verb@std::cout<<std::endl;@\\
\mbox{}\verb@std::copy(temp2.begin(), temp2.end(),@\\
\mbox{}\verb@          std::ostream_iterator<criminal>(std::cout, "\n"));@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Used in part \hyperlink{17}{17}.
\end{list}
\end{minipage}\\[4ex]
\end{flushleft}
Here is the output of our search:

\begin{flushleft} \small \label{part57}
\colorbox{light}{$\langle$output from criminal profiling example {\footnotesize \hypertarget{27d}{27d}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@--- Criminals matching the description of Suspect1 ---@\\
\mbox{}\verb@Victor Manuel Gerena@\\
\mbox{}\verb@  height: 1.68m@\\
\mbox{}\verb@  weight: 75kg@\\
\mbox{}\verb@  build : stocky@\\
\mbox{}\verb@  hair  : brown@\\
\mbox{}\verb@  eyes  : green@\\
\mbox{}\verb@  sex   : male@\\
\mbox{}\verb@  race  : hispanic@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@--- Criminals matching the description of Suspect2 ---@\\
\mbox{}\verb@Robert William Fisher@\\
\mbox{}\verb@  height: 1.83m@\\
\mbox{}\verb@  weight: 86kg@\\
\mbox{}\verb@  build : medium@\\
\mbox{}\verb@  hair  : brown@\\
\mbox{}\verb@  eyes  : blue@\\
\mbox{}\verb@  sex   : male@\\
\mbox{}\verb@  race  : white@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Not used.
\end{list}
\end{flushleft}
\chapter{Reference Manual}
\label{sec-ref-manual}
\section{API Reference}
\label{sec-apiref}

\subsection{Trivial \code{distribute} Function}
\subsubsection{Prototype}
\begin{flushleft} \small
\begin{minipage}{\linewidth}\color{blue} \label{part58}
\colorbox{light}{$\langle$prototype for the trivial distribute function {\footnotesize \hypertarget{29}{29}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@template <typename InputIterator,@\\
\mbox{}\verb@          typename OutputIteratorIfTrue,@\\
\mbox{}\verb@          typename OutputIteratorIfFalse,@\\
\mbox{}\verb@          typename Predicate>@\\
\mbox{}\verb@void distribute(InputIterator first, InputIterator last, @\\
\mbox{}\verb@                OutputIteratorIfTrue out1,@\\
\mbox{}\verb@                OutputIteratorIfFalse out2, Predicate p)@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Not used.
\end{list}
\end{minipage}\\[4ex]
\end{flushleft}
\subsubsection{Description}
Evaluates each element in the input range against the predicate 
specified; the element is copied to one of the two output iterators 
based on the result of the test.\footnote{This implies that the value 
types of the input iterator and each of the output iterators should 
be equal; failing that, the output iterator types should be copy 
constructible from objects of the input iterator's value type.} All 
elements will be placed in one of the destinations.

\subsubsection{Definition}
Defined in the header file \code{router.hpp}.

\subsubsection{Type Requirements}
\begin{itemize}
\item \code{InputIterator} models the \code{Input Iterator} concept, 
as defined in \cite{sgi-stl}. \item \code{OutputIteratorIfTrue} and 
\code{OutputIteratorIfFalse} model the \code{Output Iterator} 
concept, as defined in \cite{sgi-stl}. \item \code{Predicate} models 
the \code{Predicate} concept, as defined in \cite{sgi-stl}.
\end{itemize}

\subsubsection{Preconditions}
\begin{itemize}
\item $[\code{first},\code{last})$ is a valid range.
\end{itemize}

\subsubsection{Complexity}
$O(N)$ predicate evaluations and assignments (both average and 
worst-case) where $N$ is $\code{last}-\code{first}$.

\subsection{\code{destination} Base Class}
\subsubsection{Template Signature}
\begin{flushleft} \small
\begin{minipage}{\linewidth}\color{blue} \label{part59}
\colorbox{light}{$\langle$template signature for destination base class {\footnotesize \hypertarget{30}{30}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@template <typename T>@\\
\mbox{}\verb@destination@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Not used.
\end{list}
\end{minipage}\\[4ex]
\end{flushleft}
\subsubsection{Description}
\code{destination} defines an abstract base class from which users of 
the GDFA Library can derive wrapper classes for the 
predicate-destination pairs used by the \code{router} class.

\subsubsection{Definition}
Defined in the header file \code{router.hpp}.

\subsubsection{Template Parameters}
\begin{center}
\begin{tabular}{|p{2.25in}|p{2.25in}|}
\hline
Parameter & Description\\
\hline
\code{T} & The \code{destination}'s value type: the type of object 
filtered by the \code{destination}.\\
\hline
\end{tabular}
\end{center}

\subsubsection{Type Requirements}
None, except those imposed by derived classes.

\subsubsection{Refinement of}
\code{Copy Constructable} (as defined in \cite{sgi-stl}).

\subsubsection{Valid Expressions}
\begin{center}
\begin{tabular}{|p{1.75in}|p{1in}|p{1.75in}|}
\hline
Expression & Return Type & Semantics\\
\hline
\code{distribute(o)} & \code{bool} & When this function is called on 
an object \code{o} that is being examined. The function should return 
\code{true} if and only if the given destination is the last to 
evaluate the item \code{o} (that is, the router should stop 
processing it), \code{false} else.\\
\hline
\end{tabular}
\end{center}

\subsection{\code{router} Class}
\subsubsection{Prototype}
\begin{flushleft} \small
\begin{minipage}{\linewidth}\color{blue} \label{part60}
\colorbox{light}{$\langle$template signature for router class {\footnotesize \hypertarget{31}{31}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@template <typename T>@\\
\mbox{}\verb@router<T>@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Not used.
\end{list}
\end{minipage}\\[4ex]
\end{flushleft}
\subsubsection{Definition}
Defined in the header file \code{router.hpp}.

\subsubsection{Template Parameters}
\begin{center}
\begin{tabular}{|p{2.25in}|p{2.25in}|}
\hline
Parameter & Description\\
\hline
\code{T} & The \code{router}'s value type: the type of object 
distributed by the \code{router}.\\
\hline
\end{tabular}
\end{center}

\subsubsection{Refinement of}
\code{Default Constructable}, \code{Copy Constructable}, 
\code{Assignable}.

\subsubsection{Members}
\begin{center}
\begin{tabular}{|p{2.25in}|p{2.25in}|}
\hline
Member & Description\\
\hline
\code{priority\_level} & Internal class for specifying the relative 
priority of destinations managed by the router. Instances of this 
class can be compared with the less-than, greater-than, and equality 
operators.\\
\hline
\code{low\_priority}, \code{normal\_priority}, \code{high\_priority}, 
\code{urgent\_priority} & 	The four allowable priority levels for 
destinations added to the router. Each is a static instance of 
\code{router::priority\_level}.\footnotemark\\
\hline
\code{router()} & Default constructor; creates an empty 
\code{router}.\\
\hline
\code{template $<$typename Iterator$>$ router(Iterator first, 
Iterator last, priority\_level priority=normal\_priority)} & 
Constructor; creates a \code{router} that manages the 
\code{destination} objects held in the range specified. The 
destinations found in the range must be instantiated from a sub-class 
of \code{destination$<$T$>$}. The priority selected will be assigned 
to every \code{destination} in the range.\\
\hline
\code{$\sim$router()} & Destructor.\\
\hline
\code{template $<$typename Iterator$>$ void distribute(Iterator 
item)} & Allows each destination to evaluate the object at the 
location referenced by the given iterator until a match is found or 
all destinations have been considered.\footnotemark\\
\hline
\code{template $<$typename Iterator$>$ void distribute(Iterator 
first, Iterator last)} & Invokes \code{distribute} for each iterator 
in the range specified.\\
\hline
\code{template $<$typename Destination$>$ void add\_destination(const 
Destination\& d, priority\_level priority = normal\_priority)} & Adds 
the given \code{destination} to the group managed by the 
\code{router}: its place in the group will be determined by the 
assigned priority. The \code{destination} given must be instantiated 
from a sub-class of \code{destination$<$T$>$}. The priority level 
must be one of the four defined by \code{router$<$T$>$}.\\
\hline
\end{tabular}
\end{center}

\footnotetext[2]{The implementation of the priority levels is trivial 
and thus, not expensive; the only reason for their existence is to 
limit the range of priorities.} \footnotetext[3]{The time bound on 
this operation is $O(N)$, where $N$ is the number of destinations.}

\begin{center}
\begin{tabular}{|p{2.25in}|p{2.25in}|}
\hline
Member & Description\\
\hline
\code{template $<$typename Destination$>$ void set\_default(const 
Destination\& d)} & Adds a default \code{destination} to the 
\code{router}; the default will be used whenever no match is found 
for an input. The \code{destination} given must be instantiated from 
a sub-class of \code{destination$<$T$>$}. No priority is assigned to 
the default \code{destination}.\footnotemark\\
\hline
\code{void remove\_default()} & Removes a default destination; if 
there is no default, no action is taken.\\
\hline
\end{tabular}
\end{center}

\footnotetext[4]{The actual priority can be said to be less than 
\code{router::low\_priority.}}

\chapter{Design Issues and Source Code}
This chapter will discuss the design issues involved in the creation 
of the GDFA Library; for each topic presented, the relevant source 
code will be included for reference. We will first review the ideas 
and concepts that led to the development of the library, and then 
revisit each individually as we show how ideas were transformed into 
implementation. Extra attention should be given to the explanation of 
terminology, as some words used here have definitions that are quite 
different from their more common meanings.

\section{Concept of Distribution and Filtering}
The foundation for the GDFA Library is in the simple 
\code{distribute} function documented earlier. To see how this 
utility function serves as the premise for the more advanced 
\code{router} and \code{destination} classes, we need to revisit the 
first example presented in the User's Guide (Chapter 
\ref{sec-user-guide}). Recall that the example programme was managing 
batch jobs that ran as part of daily database maintenance procedures; 
jobs were split into two categories---\code{normal} and 
\code{urgent}---and then executed in terms of their relative 
priority. The \code{distribute} function was used to filter the jobs 
into the correct container directly from the input stream, so that no 
unnecessary copying was performed. 

\subsection{Introduction to Distribution and Filtering}
To see how this generic utility offers a real value to the 
programmer, let us first consider an applications-specific solution 
to this I/O problem---it takes a file name and two 
\code{std::vector}s in which to copy the data:

\begin{flushleft} \small
\begin{minipage}{\linewidth}\color{blue} \label{part61}
\colorbox{light}{$\langle$database distribute example 1 {\footnotesize \hypertarget{35}{35}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@void distribute(const string& fileName, @\\
\mbox{}\verb@                vector<DatabaseJob>& urgent, @\\
\mbox{}\verb@                vector<DatabaseJob>& normal)@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  ifstream inputFile(fileName);@\\
\mbox{}\verb@  DatabaseJob job;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  while(inputFile>>job)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    if(job.IsHighPriority())@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      urgent.push_back(job);@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@    else@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      normal.push_back(job);@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@}@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Not used.
\end{list}
\end{minipage}\\[4ex]
\end{flushleft}
\subsection{Generic Input Range}
The first thing to note is that we have restricted our source of 
input to a formatted file---we can never use this code to filter 
objects in an existing container or another stream (such as the 
standard input stream, \code{std::cin}). We would like to have the 
extensibility found in STL algorithms and allow users to transfer 
data similarly to the way \code{std::copy} moves elements from one 
range to another. C++ templates can be used to parameterise the type 
of input and remove this restriction.

A generic range of input, then, is the first definitive aspect of our 
filtering component. The range is defined by two parameterised input 
iterators (specified by the \code{InputIterator} parameter), which 
may traverse either streams or containers. Note that in the case 
where the input iterator is a \code{std::istream\_iterator}, the 
\code{operator>>} method will still be necessary to read in the 
\code{DatabaseJob} objects.

\begin{flushleft} \small
\begin{minipage}{\linewidth}\color{blue} \label{part62}
\colorbox{light}{$\langle$database distribute example 2 {\footnotesize \hypertarget{36}{36}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@template <typename InputIterator>@\\
\mbox{}\verb@void distribute(InputIterator begin, @\\
\mbox{}\verb@                InputIterator end, @\\
\mbox{}\verb@                vector<DatabaseJob>& urgent, @\\
\mbox{}\verb@                vector<DatabaseJob>& normal)@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  while(begin!=end)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    DatabaseJob job=*begin++;@\\
\mbox{}\verb@@\\
\mbox{}\verb@    if(job.IsHighPriority())@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      urgent.push_back(job);@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@    else@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      normal.push_back(job);@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@}@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Not used.
\end{list}
\end{minipage}\\[4ex]
\end{flushleft}
\subsection{Generic Output}
The next concern is that the function names a specific container for 
the filtered \code{DatabaseJob} objects. Given the standard iterator 
interface used by all STL containers and streams, there is no reason 
this code should force users to put their elements in a 
\code{std::vector}. Users should be allowed to specify any 
destination for the \code{DatabaseJob} objects in the same way they 
are allowed to specify a generic source of input; this output 
destination might be a container like \code{std::set} or a stream 
such as \code{std::cout}.

A generic destination, however, is only part of the answer to the 
question of how to parameterise the output range. Why does the output 
have to be composed of \code{DatabaseJob} objects? We are looking for 
an efficient, generic solution that can be easily reused, and there 
is no reason that this algorithm cannot be applied to other types of 
data. Our function is reading in objects and putting them in one of 
two containers given the results of a conditional, which is not 
database-specific at all. By replacing all references to a vector of 
\code{DatabaseJobs} with a set of output iterators, the 
\code{distribute} function takes on a completely generic I/O 
interface. \code{OutputIteratorIfTrue} and 
\code{OutputIteratorIfFalse} are the two output iterator types 
associated with the destinations that are chosen given the Boolean 
result of the predicate---they are independent of each other and may 
be of different types.  

\begin{flushleft} \small
\begin{minipage}{\linewidth}\color{blue} \label{part63}
\colorbox{light}{$\langle$database distribute example 3 {\footnotesize \hypertarget{37a}{37a}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@template <typename InputIterator, @\\
\mbox{}\verb@          typename OutputIteratorIfTrue,@\\
\mbox{}\verb@          typename OutputIteratorIfFalse>@\\
\mbox{}\verb@void distribute(InputIterator begin, InputIterator end, @\\
\mbox{}\verb@                OutputIteratorIfTrue out1, OutputIteratorIfFalse out2)@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  while(begin!=end)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    typename iterator_traits<InputIterator>::value_type item;@\\
\mbox{}\verb@    item=*begin++;@\\
\mbox{}\verb@    item.IsHighPriority() ? *out1++=item : *out2++=item;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@}@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Not used.
\end{list}
\end{minipage}\\[4ex]
\end{flushleft}
\subsection{Generic Predicate}
There is one glaring problem left in the algorithm, and that is the 
call to \code{DatabaseJob::IsHighPriority}. Our function refers to no 
specific type, and even if the type in question is guaranteed to be a 
class (which it is certainly not), it is not reasonable to demand 
that the class have an \code{IsHighPriority} member. The correct 
approach to making this solution completely reusable is to use 
predicates in the same way that the standard library algorithms do. 
In the final version of \code{distribute}, a fifth parameter has been 
added to allow programmers to name the comparator that should be used 
to analyse the data. This component now accepts a generic range of 
input, evaluates it with any user-defined predicate (specified by the 
\code{Predicate} parameter), and places it in one of two independent 
destinations.

\begin{flushleft} \small
\begin{minipage}{\linewidth}\color{blue} \label{part64}
\colorbox{light}{$\langle$the distribute function {\footnotesize \hypertarget{37b}{37b}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@template <typename InputIterator, @\\
\mbox{}\verb@          typename OutputIteratorIfTrue,@\\
\mbox{}\verb@          typename OutputIteratorIfFalse,@\\
\mbox{}\verb@          typename Predicate>@\\
\mbox{}\verb@void distribute(InputIterator begin, InputIterator end, @\\
\mbox{}\verb@                OutputIteratorIfTrue out1, OutputIteratorIfFalse out2,@\\
\mbox{}\verb@                Predicate p)@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  while (begin != end)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    typename std::iterator_traits<InputIterator>::value_type@\\
\mbox{}\verb@     item=*begin++;@\\
\mbox{}\verb@    p(item) ? *out1++=item : *out2++=item;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@}@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Used in part \hyperlink{45}{45}.
\end{list}
\end{minipage}\\[4ex]
\end{flushleft}
\section{A More Generic Phrasing of Distribution and Filtering}
In order to further generalise the algorithm and add more power to 
its filtering capabilities, it was necessary to remove the 
restriction on the number of destinations to which the input elements 
could be written. With this limitation eliminated, users could filter 
data to one or more locations based on a set of criteria that was 
more complex than a single Boolean check---elements could be 
evaluated against multiple, independent predicates and have compound 
actions performed against them. This was by far the most complicated 
issue in the development of the library, as it required the 
construction of a full supporting framework to offer flexibility 
without decreasing usability. It was clear that the resulting set of 
classes and/or functions would have to pair the multiple predicates 
and output destinations. The \code{router} class, along with the 
helper \code{destination} class, offers this advanced functionality 
by building on the ideas presented so far.

\subsection{Arbitrary Number of Destinations}
Our \code{router} class manages a set of predicate-output pairs 
through which it filters incoming data. Our \code{router} class 
manages a set of predicate-output pairs through which it filters 
incoming data. The most complex aspect of \code{router} is not the 
implementation of its methods but rather the parameterisation of 
their parameters---the class makes extensive use of member templates 
in order to provide the desired flexibility. The aforementioned pairs 
are really instances of the \code{destination} class.

The first building block in the GDFA framework is the 
\code{destination} class for evaluating input and performing some 
action against it. Users may extend the class any way they wish, but 
they must override the pure virtual function \code{distribute} or the 
derived class will remain abstract.

\begin{flushleft} \small
\begin{minipage}{\linewidth}\color{blue} \label{part65}
\colorbox{light}{$\langle$the destination class {\footnotesize \hypertarget{38}{38}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@template <typename T>@\\
\mbox{}\verb@class destination@\\
\mbox{}\verb@{@\\
\mbox{}\verb@public:@\\
\mbox{}\verb@  virtual ~destination() {}@\\
\mbox{}\verb@  virtual bool distribute(const T& element)=0;@\\
\mbox{}\verb@};@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Used in part \hyperlink{45}{45}.
\end{list}
\end{minipage}\\[4ex]
\end{flushleft}
\subsection{Creating Derived Classes from \code{destination}}
The purpose of the \code{distribute} function is to perform an action 
against the parameter it receives. Technically, there is no limit or 
restriction on what the implementation can or should do, but the 
problems that the framework hopes to solve tend to follow a common 
pattern: the element is tested against some criteria and written to 
an output based on the result of that test. The Boolean value 
returned by the function should be true if the router is to stop 
evaluation of the current element---that is, if it should move on to 
the next element in the input range without passing the current 
element to other destinations. The User's Guide (Chapter 
\ref{sec-user-guide}) has multiple examples to demonstrate how the 
\code{destination} class can be used as a base for programmer tests, 
but the basic idea behind most implementations can be described with 
the following pseudo-code:

\begin{flushleft} \small
\begin{minipage}{\linewidth}\color{blue} \label{part66}
\colorbox{light}{$\langle$deriving from destination {\footnotesize \hypertarget{39}{39}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@template <typename Output>@\\
\mbox{}\verb@class new_destination : destination<type>@\\
\mbox{}\verb@{@\\
\mbox{}\verb@private: @\\
\mbox{}\verb@  Output out;@\\
\mbox{}\verb@@\\
\mbox{}\verb@public:@\\
\mbox{}\verb@  new_destination(Output _out) : out(_out) {} @\\
\mbox{}\verb@@\\
\mbox{}\verb@  bool distribute(const type& element)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    if(some test against element)@\\
\mbox{}\verb@      write element to output@\\
\mbox{}\verb@         @\\
\mbox{}\verb@      return true to stop evaluation@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@};@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Not used.
\end{list}
\end{minipage}\\[4ex]
\end{flushleft}
\subsection{The \code{destination\_handle} Class}
For any range of input, users can create multiple \code{destination}s 
through which to filter the elements---for each \code{destination} 
created, an instance is added to the \code{router}, which will pass 
the input through the \code{destination}s until it is told to stop or 
until it has considered every one. Because users must be able to 
create and use multiple different destination sub-classes to be 
placed in a single \code{router}, the internal mechanism for handling 
these destination objects is more complicated than initially planned. 
Fortunately, the user interface is not affected by this complexity, 
and users who can understand the above pseudo-derivation from 
\code{destination} can use the GDFA Library effectively. 

\subsubsection{Introduction to Handles}
The \code{router} class manages the destination objects created by 
the user in a single container. Holding many objects of different 
sub-types in one container without complicating the interface was a 
challenge, but one that was necessary since we did not want to limit 
the number of destinations that a router could manage. Applications 
that used the library to filter large batches of data might have 
hundreds of predicates to evaluate the many possible attributes 
associated with their data; imposing a limit on the number of 
destinations would be imposing a limit on the acceptance of the 
library in mainstream software development. Furthermore, a class 
interface that only accepted $N$ destinations but without the aid of 
member template functions would be extremely cumbersome to programme, 
with much of the parameterisation information having to be specified 
explicitly. Programming \code{router} to hold a single container of 
destinations so that all actions could be performed against them in a 
generic way was essential to both interface and implementation 
simplicity---the aforementioned increase in complexity came with the 
added layer of abstraction within \code{router} to allow for the 
generic treatment of \code{destination} objects. 

The \code{destination}s are held indirectly by the \code{router} 
class through an handle---a wrapper that holds a pointer to a 
\code{destination} and performs all of the dynamic memory management 
for that pointer. This handle class, \code{destination\_handle}, is a 
member of \code{router}, and is internal to the framework---it is 
used in combination with member template functions to provide 
seamless interaction with the user-defined \code{destination}s. The 
basic functionality of the handle---its memory management---is 
demonstrated below; \code{destination\_handle} uses reference 
counting to offer copying and assignment semantics similar to 
pointers while preventing memory leaks and/or data corruption. It is 
assumed the reader is familiar with the basic ideas behind reference 
counting, and we will not review them here. The key aspect to note is 
that the handle holds a pointer to a \code{destination} and takes 
advantage of that class's virtual functions to invoke the correct 
method(s) in the concrete sub-class. Thus, object-oriented 
polymorphism has provided a simple solution to the problem of 
managing objects of different types in a single container.

\begin{flushleft} \small \label{part67}
\colorbox{light}{$\langle$handle class used to store destinations {\footnotesize \hypertarget{40}{40}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@class destination_handle@\\
\mbox{}\verb@{@\\
\mbox{}\verb@private:@\\
\mbox{}\verb@  destination<T> *dest;@\\
\mbox{}\verb@  std::size_t *referenceCount;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  void destroy()@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    if(--*referenceCount==0)@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      delete referenceCount;@\\
\mbox{}\verb@      delete dest;@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@@\\
\mbox{}\verb@  priority_level priority;@\\
\mbox{}\verb@@\\
\mbox{}\verb@public:@\\
\mbox{}\verb@  @\hbox{\colorbox{light}{$\langle$member template constructor {\footnotesize \hyperlink{42a}{42a}}$\rangle$}}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@  destination_handle(const destination_handle& copy)@\\
\mbox{}\verb@  :dest(copy.dest),@\\
\mbox{}\verb@   referenceCount(copy.referenceCount)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    ++*referenceCount;@\\
\mbox{}\verb@    priority=copy.priority;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@@\\
\mbox{}\verb@  destination_handle& operator=@\\
\mbox{}\verb@   (const destination_handle& rhs)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    ++*rhs.referenceCount;@\\
\mbox{}\verb@@\\
\mbox{}\verb@    destroy();@\\
\mbox{}\verb@@\\
\mbox{}\verb@    dest=rhs.dest;@\\
\mbox{}\verb@    referenceCount=rhs.referenceCount;@\\
\mbox{}\verb@    priority=rhs.priority;@\\
\mbox{}\verb@                                @\\
\mbox{}\verb@    return *this;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@@\\
\mbox{}\verb@  bool operator< (const destination_handle& rhs) const@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    return priority<rhs.priority;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@@\\
\mbox{}\verb@  bool operator>(const destination_handle& rhs) const@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    return rhs<*this;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@@\\
\mbox{}\verb@  ~destination_handle()@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    destroy();@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@            @\\
\mbox{}\verb@  @\hbox{\colorbox{light}{$\langle$destination accessor function {\footnotesize \hyperlink{42b}{42b}}$\rangle$}}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@};@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Used in part \hyperlink{42c}{42c}.
\end{list}
\end{flushleft}
\subsubsection{Abstracting Away from Pointers}
One thing it did not solve, however, was the requirement that users 
pass a pointer to each \code{destination} they added to the 
\code{router}. This was undesirable both because it decreased 
usability (users should be able to use the \code{router} without 
having to do any dynamic memory management) and increased the 
potential for bugs (\code{destination}s declared locally on the stack 
which went out of scope after being added to the router would raise 
exceptions and corrupt programme results). We wanted the insertion 
methods of the \code{router} class to be similar to those of STL 
containers---the user would pass a reference to the given destination 
and know that an independent copy was being kept; such an interface 
is as simple as possible in terms of C++ language constructs. The 
\code{destination\_handle} class uses a member template constructor 
to create a dynamically allocated copy of the given destination; this 
method is central to the \code{router}'s ability to accept any class 
built off the GDFA \code{destination} without having to include any 
reflection-like code.

\begin{flushleft} \small
\begin{minipage}{\linewidth}\color{blue} \label{part68}
\colorbox{light}{$\langle$member template constructor {\footnotesize \hypertarget{42a}{42a}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@template <typename Destination>@\\
\mbox{}\verb@destination_handle(const Destination& d, priority_level _priority)@\\
\mbox{}\verb@:priority(_priority), @\\
\mbox{}\verb@ dest(new Destination(d)),@\\
\mbox{}\verb@ referenceCount(new std::size_t(1)){}@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Used in part \hyperlink{40}{40}.
\end{list}
\end{minipage}\\[4ex]
\end{flushleft}
\subsubsection{Access to Functionality of \code{destination}}
The \code{router} accesses the distribution functionality written by 
the user with a simple wrapper function that passes along the given 
element to the \code{destination} class. We will revisit the handle 
class later when discussing the priority of \code{destination}s 
vis-\'a-vis input evaluation.

\begin{flushleft} \small
\begin{minipage}{\linewidth}\color{blue} \label{part69}
\colorbox{light}{$\langle$destination accessor function {\footnotesize \hypertarget{42b}{42b}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@bool distribute(const T& element)@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  return dest->distribute(element);@\\
\mbox{}\verb@}@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Used in part \hyperlink{40}{40}.
\end{list}
\end{minipage}\\[4ex]
\end{flushleft}
\subsection{The \code{router} Class}
With a generic handle class to take away the issues of polymorphism 
presented by the different \code{destination} sub-classes, the 
implementation of \code{router} becomes fairly simple. Most of the 
functionality is similar to that of an ordinary STL container, with 
the significant addition being the processing of an input ranges 
through the set of destinations according to user preference. The 
most basic methods of router are presented below to give an idea of 
its internal structure before presenting the input processing methods.

\begin{flushleft} \small \label{part70}
\colorbox{light}{$\langle$the router class {\footnotesize \hypertarget{42c}{42c}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@template <typename T>@\\
\mbox{}\verb@class router@\\
\mbox{}\verb@{@\\
\mbox{}\verb@public:@\\
\mbox{}\verb@  typedef unsigned int priority_level;@\\
\mbox{}\verb@  static const priority_level low_priority=0;@\\
\mbox{}\verb@  static const priority_level normal_priority=1;@\\
\mbox{}\verb@  static const priority_level high_priority=2;@\\
\mbox{}\verb@  static const priority_level urgent_priority=3;@\\
\mbox{}\verb@@\\
\mbox{}\verb@private:@\\
\mbox{}\verb@  @\hbox{\colorbox{light}{$\langle$handle class used to store destinations {\footnotesize \hyperlink{40}{40}}$\rangle$}}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@  std::vector<destination_handle> destinations;@\\
\mbox{}\verb@  destination_handle *defaultDestination;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  // not implemented: prohibited@\\
\mbox{}\verb@  router(const router& copy);@\\
\mbox{}\verb@  router& operator=(const router& rhs);@\\
\mbox{}\verb@@\\
\mbox{}\verb@public:@\\
\mbox{}\verb@  router() : defaultDestination(NULL) {}@\\
\mbox{}\verb@      @\\
\mbox{}\verb@  template <typename OutputIterator>@\\
\mbox{}\verb@  router(OutputIterator first, OutputIterator last)@\\
\mbox{}\verb@  :defaultDestination(NULL)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    std::copy(first, last,@\\
\mbox{}\verb@              std::back_inserter(destinations));@\\
\mbox{}\verb@    std::make_heap(first, last);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@@\\
\mbox{}\verb@  ~router()@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    remove_default();@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@@\\
\mbox{}\verb@  template <typename InputIterator>@\\
\mbox{}\verb@  void distribute(InputIterator item)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    typename std::vector<destination_handle>::iterator i;@\\
\mbox{}\verb@@\\
\mbox{}\verb@    for (i=destinations.begin(); i!=destinations.end();@\\
\mbox{}\verb@         ++i)@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      if(i->distribute(*item))@\\
\mbox{}\verb@      {@\\
\mbox{}\verb@        break;@\\
\mbox{}\verb@      }@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@@\\
\mbox{}\verb@    if(i==destinations.end() && defaultDestination)@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      defaultDestination->distribute(*item);@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@@\\
\mbox{}\verb@  template <typename InputIterator>@\\
\mbox{}\verb@  void distribute(InputIterator first, InputIterator last)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    while(first!=last)@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      distribute(first++);@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@@\\
\mbox{}\verb@  template <typename Destination>@\\
\mbox{}\verb@  void add_destination(const Destination& d,@\\
\mbox{}\verb@                       int _priority=normal_priority)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    destinations.push_back(destination_handle(d,_priority));@\\
\mbox{}\verb@    std::push_heap(destinations.begin(),@\\
\mbox{}\verb@    destinations.end());@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@@\\
\mbox{}\verb@  template <typename Destination>@\\
\mbox{}\verb@  void set_default(const Destination& d)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    remove_default();@\\
\mbox{}\verb@    defaultDestination=@\\
\mbox{}\verb@     new destination_handle(d,normal_priority);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@@\\
\mbox{}\verb@  void remove_default()@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    if(defaultDestination)@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      delete defaultDestination;@\\
\mbox{}\verb@      defaultDestination=NULL;@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@};@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Used in part \hyperlink{45}{45}.
\end{list}
\end{flushleft}
\subsubsection{Default \code{destination}}
The default \code{destination} is an optional component that provides 
a way to catch any elements in the input range that did not pass any 
of the tests conducted by the \code{router}'s \code{destination}s. If 
no default is set and an element is passed to every destination 
without one of them returning true (to tell the router to stop 
evaluation), no action will be taken---the router will simply move on 
to the next element. When a default is specified, however, an element 
that does not match up against any regular \code{destination} will be 
given to the default for further processing. 

We decided to keep the default \code{destination} completely separate 
from the other \code{destination} objects in order to simplify the 
implementation---the only other option would be to keep it at the end 
of the container of \code{destination}s, and this would be cumbersome 
to maintain even without the existing priority scheme that will be 
discussed later. Storing the default as a dynamically allocated 
resource (that is, in terms of a pointer) allowed us to easily tell 
whether a default existed (by comparing the pointer to NULL) and to 
access it without using any obtuse iterator trickery. 

From the programmer's perspective, a default \code{destination} class 
need not be any different from other sub-classes of 
\code{destination}. The only difference in its use is that instances 
of the default \code{destination} must be added or removed with 
special member functions (\code{set\_default} and 
\code{remove\_default}) rather than the normal 
\code{add\_destination} method. Regarding implementation, the only 
complication that arises from our choices is that \code{router} now 
owns a dynamic resource, and must implement a destructor to prevent 
memory leaks.

\subsubsection{Priorities}
The \code{router} class offers the ability to assign priorities to 
the \code{destination}s it manages. Four built-in priorities 
(\code{low\_priority}, \code{normal\_priority}, 
\code{high\_priority}, and \code{urgent\_priority}) are available to 
users so that they can ensure that some \code{destination}s are 
always considered before others, no matter the order in which they 
were added. The user specifies the \code{destination}'s priority when 
adding it to the \code{router}, with the default being 
\code{normal\_priority} (this means that if the user has no interest 
in using the priority scheme, he or she will not be affected by it). 
As each \code{destination} is inserted, the \code{router} uses the 
binary heap functions of the Standard Library to adjust the 
\code{std::vector} of \code{destination} objects it keeps; by storing 
the elements as a binary heap, the \code{router} is able to keep them 
prioritised very efficiently (the amount of copying that will be done 
for each heap adjustment will be equal to $O(\lg N)$, and the copies 
themselves will only be of the lightweight handles, not the actual 
\code{destination} objects).

\section{Trivial \code{distribute}, \code{destination}, and \code{router} Code}
To finish everything up, we combine everything and define the header 
file which will form the basis of the GDFA Library. All that we need 
to do is add the standard \code{\#ifdef}-\code{\#endif} block to 
avoid issues with multiple inclusions of the file, include some 
standard library components, and define the \code{gdfa} namespace.

\begin{flushleft} \small \label{part71}
\verb@"router.hpp"@ {\footnotesize \hypertarget{45}{45} }$\equiv$
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@#ifndef _router_@\\
\mbox{}\verb@#define _router_@\\
\mbox{}\verb@@\\
\mbox{}\verb@#include <algorithm>@\\
\mbox{}\verb@#include <functional>@\\
\mbox{}\verb@#include <iterator>@\\
\mbox{}\verb@#include <vector>@\\
\mbox{}\verb@@\\
\mbox{}\verb@namespace gdfa@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  @\hbox{\colorbox{light}{$\langle$the distribute function {\footnotesize \hyperlink{37b}{37b}}$\rangle$}}\verb@@\\
\mbox{}\verb@  @\hbox{\colorbox{light}{$\langle$the destination class {\footnotesize \hyperlink{38}{38}}$\rangle$}}\verb@@\\
\mbox{}\verb@  @\hbox{\colorbox{light}{$\langle$the router class {\footnotesize \hyperlink{42c}{42c}}$\rangle$}}\verb@@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@\\
\mbox{}\verb@#endif@\\
\mbox{}\verb@@
\end{list}
\vspace{-2ex}
\end{flushleft}
\chapter{Testing Approach and Results}
\label{appendix-test-code}

\section{Overview}
This section includes a description and motivation behind all of the 
tests performed on the Generic Distribution and Filtering Algorithms. 
The results of those tests and a discussion of the results are also 
presented here.

Our testing strategy consists of tests for performance and 
correctness. The performance tests consist of timed tests and 
operation counting. Correctness and Performance testing was performed 
on all key features of the Generic Distribution and Filtering 
Algorithms. Correctness testing was performed on many conceivable use 
cases implemented on a thorough set of built-in types and STL types. 
Timed tests and Operation Counts were performed in various 
configurations in order to time (and, likewise, to count) different 
aspects of the algorithms.

\subsection{Notation}
In some of the following tests, the order, or $O$-bound (asymptotic 
complexity), of the algorithm is tested. The algorithm is initially 
assumed to operate in $O(MN)$ time. $N$ represents the algorithm 
input size or the number of elements fed through the algorithm. These 
are the elements to be distributed. $M$ represents the number of 
destination classes used (including the default destination).

The term ``growth rate'' used here is defined as the increase in 
measured execution time when $N$ is doubled. Hence, we can define 
growth rate by the formula $G(N)=T(N)/T(N/2)$ where $G(N)$ is the 
growth function and $T(N)$ is the measured execution time of an 
$N$-element input. The growth rate for an algorithm of linear 
complexity would be $2$. This measurement allows us to look more 
closely at the time increase relative to $N$. The increase from $N/2$ 
to $N$ is precisely calculated and graphed. In all cases the 
calculated growth rate is approximately $2$, which indicates a linear 
time complexity.

\subsection{Computer Testing Configuration}
The performance tests presented here were performed on an IBM 
ThinkPad Computer with $1.8$ GHz Mobile Pentium $4$ with Intel 
SpeedStep technology and $256$MB of RAM. All code was compiled with 
g++ version $3.2$ with the ``-O3'' flag. Performance on additional 
platforms, in particular the Rensselaer Polytechnic Institute CS 
Department Solaris Server (sparc-sun-solaris$2.8$)(compiled under g++ 
$3.2$) was tested and relative ($O$-bound) performance was comparable 
to that generated by the Pentium machine.

The correctness tests presented here were also performed on an IBM 
ThinkPad Computer with $1.8$ GHz Mobile Pentium $4$ with Intel 
SpeedStep technology and $256$MB of RAM. All code was compiled with 
g++ version $3.2$ with the ``-O3'' flag. The correctness tests were 
run on additional platforms, in particular a Macintosh ibook with a 
$700$MHz PowerPC G3 processor, $640$MB RAM, running OSX $10.2.2$ and 
the results were identical.

\section{Timed Tests}
\subsection{Running Time Tests: (Time vs. N)}
The following $3$ timed tests attempt to test for $3$ different 
configurations of the algorithm. All $3$ tests are intended to 
measure the running time of the algorithm with respect to input $N$ 
(the number of elements in the input range).

\subsubsection{Timed Test 1a (Time vs. N): Each Element Distributed to m Destinations}
\paragraph{Description}
This test runs the full router class using $3$ destinations plus $1$ 
default destination. This configuration attempts to capture a 
worst-case for the algorithm. As such, each destination object will 
insert the element into their respective destination, and then pass 
the element on to the next destination object (by returning 
\code{false}). The code implementing this test can be found in 
Appendix \ref{sec-code-test1a}.

\paragraph{Test Objective}
This test determines the order of the algorithm with respect to the 
size of the input, $N$. The input is the number of elements fed in 
through the algorithm via an iterator range.

\paragraph{Results}
\begin{figure}
\begin{center}
\includegraphics[width=5in]{timed_test_1a}
\caption{Results of Timed Test $1a$}\label{fig-r1a}
\end{center}
\end{figure}
\begin{figure}
\begin{center}
\includegraphics[width=5in]{timed_test_1a_e}
\caption{Growth Rate of Timed Test $1a$}\label{fig-r1a_e}
\end{center}
\end{figure}

The results of this test, as represented in Figure \ref{fig-r1a}, 
show that the algorithm runs in linear time with respect to $N$. The 
growth rate results results, as represented in Figure \ref{fig-r1a_e} 
confirm these findings; in fact, the growth rate graph shows the 
temporal complexity of the algorithm to be consistently linear. This 
test is very useful in showing the variation in running time because 
it emphasises the most significant (time-wise) part of the algorithm, 
which is inserting the element into the destination via an iterator. 
As explained above, this test forces a worst-case scenario and likely 
does not represent a typical implementation. This atypical 
configuration combined with the observation that element insertion 
dominates the running time (and masks the decision making time) 
results in the need for additional testing.

\subsubsection{Timed Test 1b (Time vs. N): Each Element Distributed to Exactly 1 Destination}
\label{sec-test-1b}
\paragraph{Description}
This test runs the full router class using $3$ destinations plus $1$ 
default destination. This configuration attempts to capture a typical 
case for the algorithm. As such, the elements read in on the input 
iterator will each be distributed to $1$ and only $1$ destination. 
This is accomplished as follows. The primary destinations are set up 
so that the elements are always passed through to the next 
destination. Each element is then distributed by the default 
destination. The code implementing this test can be found in Appendix 
\ref{sec-code-test1b}.

\paragraph{Test Objective}
The purpose of this test is to determine the order of the algorithm 
with respect to the size of the input, $N$. The input is the number 
of elements fed through the algorithm via an iterator range.

\paragraph{Results}
\begin{figure}
\begin{center}
\includegraphics[width=5in]{timed_test_1b}
\caption{Results of Timed Test $1b$}\label{fig-r1b}
\end{center}
\end{figure}
\begin{figure}
\begin{center}
\includegraphics[width=5in]{timed_test_1b_e}
\caption{Growth Rate of Timed Test $1b$}\label{fig-r1b_e}
\end{center}
\end{figure}

The results of this test, as presented in Figure \ref{fig-r1b}, show 
that the algorithm runs in linear time with respect to $N$. The 
growth rate results, as represented in Figure \ref{fig-r1b_e} confirm 
these findings. The growth rate graph, in fact, demonstrates that the 
temporal complexity of the algorithm is consistently linear. This 
test reflects a different case than Test $1a$ and is arguably a more 
typical case. This test de-emphasises, to some extent, the most 
significant (time-wise) part of the algorithm, which is inserting the 
element into the destination via an iterator. This test creates a 
worst-case scenario regarding the number of decisions concerned 
because, although each element is distributed by just one destination 
object, it is always the default destination. This typical 
configuration complements and confirms the above results.

\subsubsection{Timed Test 1c: (Time vs. N) - Each Element Distributed to 0 Destinations}
\paragraph{Description}
This test runs the full router class using $3$ destinations plus $1$ 
default destination. This configuration attempts to capture the 
decision making time complexity of the algorithm. To do this, the 
destination predicates were designed so that every element fit into 
every category and every destination class passed the element to each 
succeeding destination class. Therefore, $M$ decisions were made for 
each element. However, in order to measure this, the time of the 
insertion of the element into the input iterator had to minimise. 
Therefore, each destination does not actually insert the element, it 
just decides if it should and passes the element on to the next 
destination (by returning \code{false}). Each destination object will 
insert the element into their respective destination, and then pass 
the element on to the next destination object (by returning 
\code{false}). The code implementing this test can be found in 
Appendix \ref{sec-code-test1c}.

\paragraph{Test Objective}
The purpose of this test is to determine the order of the algorithm 
with respect to the size of the input, $N$. The input is the number 
of elements fed through the algorithm via an iterator range. This 
test is designed to factor out the time component associated with the 
insertion of the element via the input iterator in the destination 
object because this time is independent of this algorithm. This 
enables us to more accurately measure the other aspects of this 
algorithm.

\paragraph{Results}
\begin{figure}
\begin{center}
\includegraphics[width=5in]{timed_test_1c}
\caption{Results of Timed Test $1c$}\label{fig-r1c}
\end{center}
\end{figure}
\begin{figure}
\begin{center}
\includegraphics[width=5in]{timed_test_1c_e}
\caption{Growth Rate of Timed Test $1c$}\label{fig-r1c_e}
\end{center}
\end{figure}

The results of this test, as represented in Figure \ref{fig-r1c}, 
show that the algorithm runs in linear time with respect to $N$. The 
growth rate results, as represented in Figure \ref{fig-r1c_e} confirm 
these findings. In fact, this growth rate graph illustrates that the 
complexity of the algorithm is perfectly linear. This test reflects a 
different case than Test $la$ and Test $1b$. This test entirely 
de-emphasises a large time component of the algorithm, which is 
inserting the element into the destination via an iterator. This test 
creates a worst-case scenario regarding the number of decisions. This 
configuration complements and confirms the above results.

\subsection{Running Time compared to M destinations (Time vs. M)}
\label{sec-tests-2}
The following $3$ timed tests attempt to test for $3$ different 
configurations of the algorithm. All $3$ tests are intended to 
measure the running time of the algorithm with respect to the number 
of destination objects added to the router object ($M$).

\subsubsection{Timed Test 2a (Time vs. M): Each Element Distributed to m Destinations}
\paragraph{Description}
This test runs the full router class using $M$ destinations plus $1$ 
default destination (where $M$ varies from $0$ to $1048576$). This 
configuration attempts to capture a worst-case for the algorithm. As 
such, each destination object will insert the element into their 
respective destination, and then pass the element on to the next 
destination object (by returning \code{false}). In this test $N$ is 
held constant. The code for this test may be found in Appendix 
\ref{sec-code-test2a}.

\paragraph{Test Objective}
The purpose of this test is to determine the order of the algorithm 
with respect to the number of destination objects added to the router 
object ($M$).

\paragraph{Results}
\begin{figure}
\begin{center}
\includegraphics[width=5in]{timed_test_2a}
\caption{Results of Timed Test $2a$}\label{fig-r2a}
\end{center}
\end{figure}
\begin{figure}
\begin{center}
\includegraphics[width=5in]{timed_test_2a_e}
\caption{Growth Rate of Timed Test $2a$}\label{fig-r2a_e}
\end{center}
\end{figure}

The results of this test show that the algorithm runs in linear time 
with respect to $M$. The growth rate results, as represented in 
Figure \ref{fig-r2a_e} confirm these findings.\footnote{See Section 
\ref{sec-efficiency-disclaimer} for a possible explanation of the 
graph's behaviour.} This test is very useful in showing the variation 
in running time because it emphasises the most significant 
(time-wise) part of the algorithm, which is inserting the element 
into the destination via an iterator. This test forces a worst-case 
scenario and likely does not represent a typical implementation. This 
atypical configuration combined with the observation that element 
insertion dominates the running time (and masks the decision making 
time) results in the need for additional testing.

\subsubsection{Timed Test 2b (Time vs. M)}
\paragraph{Description}
This test runs the full router class using $M$ destinations plus $1$ 
default destination (where $M$ varies from $0$ to $1048576$). This 
configuration attempts to capture a typical case for the algorithm. 
As such, each element is distributed by exactly $1$ destination 
object. In this test $N$ is held constant. The code for this test may 
be found in Appendix \ref{sec-code-test2b}.

\paragraph{Test Objective}
The purpose of this test is to determine the order of the algorithm 
with respect to the number of destination objects added to the router 
object ($M$).

\paragraph{Results}
\begin{figure}
\begin{center}
\includegraphics[width=5in]{timed_test_2b}
\caption{Results of Timed Test $2b$}\label{fig-r2b}
\end{center}
\end{figure}
\begin{figure}
\begin{center}
\includegraphics[width=5in]{timed_test_2b_e}
\caption{Growth Rate of Timed Test $2b$}\label{fig-r2b_e}
\end{center}
\end{figure}

The results of this test, as represented in Figure \ref{fig-r2b}, 
show that the algorithm runs in linear time with respect to $M$. The 
growth rate results, as represented in Figure \ref{fig-r2b_e} confirm 
these findings.\footnote{See Section \ref{sec-efficiency-disclaimer} 
for a possible explanation of the graph's behaviour.} This typical 
configuration confirms the results of Test $2a$.

\subsubsection{Timed Test 2c (Time vs. M)}
\paragraph{Description}
This test runs the full router class using $M$ destinations plus $1$ 
default destination (where $M$ varies from $0$ to $1048576$). This 
configuration attempts to measure the decision making time component 
and de-emphasising the insertion component. This is accomplished by 
having destinations (for the purpose of testing) that do not actually 
insert the element into the input iterator. They just make a decision 
and pass the element on to the next destination object. In this test 
$N$ is held constant. The code for this test may be found in Appendix 
\ref{sec-code-test2c}.

\paragraph{Test Objective}
The purpose of this test is to determine the order of the algorithm 
with respect to the number of destination objects added to the router 
object, $M$. This test is designed to factor out the time component 
associated with the insertion of the element via the input iterator 
in the destination object because this time is independent of this 
algorithm. This enables us to more accurately measure the other 
aspects of this algorithm.

\paragraph{Results}
\begin{figure}
\begin{center}
\includegraphics[width=5in]{timed_test_2c}
\caption{Results of Timed Test $2c$}\label{fig-r2c}
\end{center}
\end{figure}
\begin{figure}
\begin{center}
\includegraphics[width=5in]{timed_test_2c_e}
\caption{Growth Rate of Timed Test $2c$}\label{fig-r2c_e}
\end{center}
\end{figure}

The results of this test, as represented in Figure \ref{fig-r2c}, 
show that the algorithm runs in linear time with respect to $M$. The 
growth rate results, as represented in Figure \ref{fig-r2c_e} confirm 
these findings.\footnote{See Section \ref{sec-efficiency-disclaimer} 
for a possible explanation of the graph's behaviour.}  This test 
reflects a different case than Test $1a$ and Test $1b$. This test 
entirely de-emphasises a large time component of the algorithm, which 
is inserting the element into the destination via an iterator. This 
test creates a worst-case scenario regarding the number of decisions. 
This configuration complements and confirms the above results.

\subsubsection{Note Regarding Growth Rate}
\label{sec-efficiency-disclaimer}
The growth rate graphs for Section \ref{sec-tests-2} reveal some 
deviation from strict linearity. This behaviour is probably due to 
the re-allocation of memory for the \code{std::vector}'s array 
sub-structure.  The re-allocation may have occurred toward the end of 
the test run and the time required to perform this costly operation 
was not equally amortised over runs of different input sizes ($N$).

\subsection{Running Time Test (Time vs. N): Simple Version}
The test presented in this section is intended to measure the running 
time of the simple ($2$-predicate) functional version of the 
algorithm with respect to input $N$ (the number of elements in the 
input range).

\subsubsection{Description}
In this configuration, each element is distributed to exactly $1$ 
\code{destination}. This test uses the simple $2$-predicate function 
version of distribution. The \code{destination}s are set up so that 
the elements are distributed to exactly $1$ of the 
\code{destination}s. The code for this test is located in 
\ref{sec-code-test3}.

\subsubsection{Test Objective}
The purpose of this test is to determine the order of the algorithm 
with respect to the size of the input $N$. The input is the number of 
elements fed through the algorithm via an iterator range.

\subsubsection{Results}
\begin{figure}
\begin{center}
\includegraphics[width=5in]{timed_test_3}
\caption{Results of Timed Test $3$}\label{fig-r3}
\end{center}
\end{figure}
\begin{figure}
\begin{center}
\includegraphics[width=5in]{timed_test_3_e}
\caption{Growth Rate of Timed Test $3$}\label{fig-r3_e}
\end{center}
\end{figure}

The results of this test, as represented in Figure \ref{fig-r3}, show 
that the algorithm runs in linear time with respect to $N$. The 
growth rate results, as represented in Figure \ref{fig-r3_e} confirm 
these findings.\footnote{See Section 
\ref{sec-efficiency-disclaimer-3} for an explanation of the slightly 
anomalous behaviour of the graph.} This test is designed similarly to 
Test $1b$ (see Section \ref{sec-test-1b}). In this test, however, 
each element is distributed to the first (of $2$) destinations.

\subsubsection{Note Regarding Growth Rate}
\label{sec-efficiency-disclaimer-3}
The sub-linear time increases are probably due to the memory being 
re-allocated toward the end of the previous run. Then, the next run 
may not have had to re-allocate memory as many times or at all, 
resulting in sub-linear time increase for that run.

\section{Operation Counting}
This section presents a group of tests performed on the GDFA. The 
tests are constructed to reinforce the results derived from the timed 
test in {section timed tests}. As such, these tests run the GDFA in 
$5$ of the configurations used in the timed tests. These tests use 
operation counting to measure the complexity of the GDFA with respect 
to the size of the input range ($N$) and the number of 
\code{destination}s ($M$). Two of the timed tests that were performed 
were specifically designed to overcome the limitations of timing 
generic algorithms. However, since the motivation behind operation 
counting is also to overcome the limitations of timing generic 
algorithms, those $2$ previous tests do not need to be performed 
again.

The tests in this section are based on the testing method presented 
in \cite{opcounting}. These evaluation methods are useful for 
evaluation generic algorithms such as GDFA. These tests make use of 
the counting adaptors implemented \cite{opcounting}.\footnote{The 
code for this library is included in Appendix 
\ref{sec-code-counters}.} These libraries provide adaptors which 
count the operations supported by a given type. In particular, the 
tests presented in this section make use of the 
\code{iterator\_counter} and \code{value\_counter} for assignment, 
comparison and other operations. The graphs presented here compare 
the sum of the assignment operations, comparison operations, other 
operations and total operations against the GDFA variable parameters, 
specifically the size of the input range ($N$) and the number of 
\code{destination}s ($M$). 

\subsection{Operation Counts vs. N}
The following $2$ timed tests perform operation counting tests for 
$2$ different configurations of the algorithm. Both tests are 
intended to measure the assignment operations, comparison operations, 
other operations and total operations of the algorithm with respect 
to Input $N$ (the number of elements in the input range), where N 
varies from $0$ to $1048576$.

\subsubsection{Operation Counting Test 1a: Each Element Distributed to M=4 Destinations}
\paragraph{Description}
This test runs the full router class using $3$ \code{destination}s 
plus $1$ default \code{destination}. This configuration attempts to 
capture a worst-case for the algorithm. As such, each 
\code{destination} object will insert the element into its respective 
\code{OutputIterator}, then pass the element on to the next 
\code{destination} object (by returning its Boolean value 
\code{false}). The element type in this test is \code{int}.

\paragraph{Test Objective}
The objective of this test is to determine the complexity of the 
algorithm with respect to the size of the input range ($N$). The 
input is the number of elements fed through the algorithm via an 
iterator range. The code implementing this test may be found in 
Appendix \ref{sec-code-count-1a}.

\paragraph{Results}
\begin{figure}
\begin{center}
\includegraphics[width=5in]{opcount1a}
\caption{Operation Counts for Test $1a$}\label{fig-count-1a}
\end{center}
\end{figure}

The results of this test, as represented in Figure \ref{fig-count-1a} 
show that the algorithm runs in linear time with respect to $N$. This 
typical configuration confirms the results of Timed Test 1a.

\subsubsection{Operation Counting Test 1b: Each Element Distributed 1 Destination}
\paragraph{Description}
This test runs the full \code{router} class using $3$ 
\code{destination}s plus $1$ default \code{destination}. This 
configuration attempts to capture a typical case for the algorithm. 
As such, the elements read in via the input iterator will each be 
distributed to $1$ (and only $1$) \code{destination}. This is 
accomplished as follows: The primary \code{destination}s are set up 
so that the elements are always passed through to the next 
\code{destination} object (by returning the Boolean value 
\code{false}). Each element is then distributed by the default 
\code{destination}. The element type in this test is also \code{int}. 
The code for this section may be found in Appendix 
\ref{sec-code-count-1b}.

\paragraph{Test Objective}
The purpose of this test is to determine the complexity of the 
algorithm with respect to the size of the input ($N$). The input is 
the number of elements fed through the algorithm via an iterator 
range.

\paragraph{Results}
\begin{figure}
\begin{center}
\includegraphics[width=5in]{opcount1b}
\caption{Operation Counts for Test $1b$}\label{fig-count-1b}
\end{center}
\end{figure}

The results of this test, as represented in Figure 
\ref{fig-count-1b}, show that the algorithm runs in linear time with 
respect to $N$. This typical configuration confirms the results of 
Operation Counting Test $1a$ as well as Timed Test $1b$.

\subsection{Operation Counts vs. M}
The following $2$ Operation Counting tests are run on $2$ different 
configurations of the algorithm. Both tests are intended to measure 
the assignment operations, comparison operations, other operations 
and total operations of the algorithm with respect to the number of 
\code{destination} objects added to the router object $M$.

\subsubsection{Operation Counting Test 2a: Each Element Distributed to M Destinations}
\paragraph{Description}
This test runs the full \code{router} class using $M$ 
\code{destination}s plus $1$ default \code{destination} (where $M$ 
varies from $0$ to $1048576$). This configuration attempts to capture 
a worst-case scenario for the algorithm. As such, each 
\code{destination} object will insert the element into their 
respective \code{destination}, and then pass the element on to the 
next \code{destination} object (by returning the Boolean value 
\code{false}). In this test $N$ is held constant. The element type in 
this test is also \code{int}. The code for this test may be found in 
Appendix \ref{sec-code-count-2a}.

\paragraph{Test Objective}
This test aims to determine the complexity of the algorithm with 
respect to the number of destination objects ($M$) added to the 
\code{router} object.

\paragraph{Results}
\begin{figure}
\begin{center}
\includegraphics[width=5in]{opcount2a}
\caption{Operation Counts for Test $2a$}\label{fig-count-2a}
\end{center}
\end{figure}
The results of this test, as represented in Figure 
\ref{fig-count-2a}, show that the algorithm runs in linear time with 
respect to $M$. This typical configuration confirms the results of 
Timed Test $2a$.

\subsubsection{Operation Counting Test 2b: Each Element Distributed 1 Destination}
\paragraph{Description}
This test runs the full \code{router} class using $M$ 
\code{destination}s plus $1$ default \code{destination} (where $M$ 
varies from $0$ to $1048576$). This configuration attempts to capture 
a typical case for the algorithm. As such, each element is 
distributed by exactly $1$ \code{destination} object. In this test 
$N$ is held constant. The element type in this test is int. The code 
for this test may be found in Appendix \ref{sec-code-count-2b}.

A notable characteristic of the results of this test is the number of 
assignment operations. While the overall results of the test show 
that the algorithm is linear with respect to $M$, the number of 
assignment operations (\code{iterator\_counter} + 
\code{value\_counter}) is constant with respect to $M$. This is 
because each element is distributed by exactly $1$ destination object 
while the size of the input range ($N$) is held constant.

\paragraph{Test Objective}
Here, we want to determine the order (asymptotic complexity) of the 
algorithm with respect to the number of \code{destination} objects 
($M$) added to the \code{router} object.

\paragraph{Results}
\begin{figure}
\begin{center}
\includegraphics[width=5in]{opcount2b}
\caption{Operation Counts for Test $2b$}\label{fig-count-2b}
\end{center}
\end{figure}
The results of this test, as represented in Figure 
\ref{fig-count-2b}, show that the algorithm runs in linear time with 
respect to $M$. This typical configuration confirms the results of 
Operation Counting Test $2a$ as well as Timed Test $2b$.

\subsection{Simple Version: Operation Counts vs. N}
\subsubsection{Description}
In this configuration, each element is distributed to exactly $1$ 
\code{destination}. This test uses the simple $2$-predicate function 
version of \code{distribute}. The \code{destination}s are set up so 
that the elements are distributed to exactly $1$ of the 
\code{destination}s. The element type in this test is \code{int}. The 
code for this test may be found in Appendix \ref{sec-code-count-3}.

\subsubsection{Test Objective}
We wish to determine the order of the algorithm with respect to the 
size of the input range ($N$) (where $N$ varies from $0$ to 
$1048576$). The input range is the number of elements in fed through 
the algorithm via an iterator range.

\subsubsection{Results}
\begin{figure}
\begin{center}
\includegraphics[width=5in]{opcount3}
\caption{Operation Counts for Test $3$}\label{fig-count-3}
\end{center}
\end{figure}
The results of this test, as represented in Figure \ref{fig-count-3} 
show that the algorithm runs in linear time with respect to $N$. This 
test is designed similarly to Test $1b$. In this test, however, each 
element is distributed to the first (of $2$) \code{destination}s. 
This test also confirms the results of Timed Test $3$.

\subsection{Operation Counts vs. N and M}
\paragraph{Description}
To more accurately describe the behavior of the GDFA \code{router} 
functionality, we now vary both the number of \code{destination}s 
($M$) and the size of the input to be filtered ($N$). This test runs 
the full \code{router} class using $M$ \code{destination}s plus $1$ 
default \code{destination} (where $M$ varies from $0$ to $16384$) and 
$N$ input objects (where $N$ varies from $1$ to $16384$). This 
configuration attempts to capture the trends that emerge as both $M$ 
and $N$ vary. To do this, we measure the number of total operations 
of the algorithm with respect to $M$ and $N$. The code for this test 
may be found in Appendix \ref{sec-code-count-4}.

\paragraph{Test Objective}
In this test we attempt to demonstrate that the behaviour of the 
\code{router} class has $O(MN)$ asymptotic complexity with respect to 
the number of operations performed given $M$ destinations and and 
input of range size $N$.

\paragraph{Results}
\begin{figure}
\begin{center}
\includegraphics[width=5in]{opcount4}
\caption{Operation Counts for Test $4$}\label{fig-count-4}
\end{center}
\end{figure}
The results of this test, as represented in Figure \ref{fig-count-4}, 
confirm by the fact that the graph is planer that the performance of 
the \code{router} class is as expected---$O(MN)$.

\section{Correctness Tests}
This section presents a large group of tests performed on the 
\code{router} class. The tests are constructed to validate the 
performance of the Generic Distribution and Filtering Algorithms. As 
such, the tests run the algorithm in various configurations using 
various built in and standard types. The output of the GDFA along 
with the input to the GDFA is given to a correctness valid method for 
that particular test. The correctness validate method performs 
checks, calculations and comparisons to determine if the output from 
the GDFA is correct for the given input.

\subsection{Common Validation Methods}
\label{sec-common-validation-methods}
Many of the tests presented in this section use a common set of 
validate methods. (Other tests use validate methods specialised for 
those particular tests.) Code for the common set of validate methods 
is presented in Appendix \ref{sec-code-validate-common}.

\subsubsection{Common Validation 1}
The first validate method iterates through 2 groups of data and 
determines if they are identical or not. The tests for which they are 
used have a baseline data set. The baseline data set is the result of 
distributing the data using a previously validated configuration. The 
types and priorities used are different; however, the desired result 
is known to be the same. Therefore, this method can be used to 
validate configurations for which these relationships exist. The code 
for this method is located in Appendix \ref{sec-code-validate-first}.

\subsubsection{Common Validation 2 (Size Validation)}
The second validate method (validate size) works on an associative 
container of elements (\code{set}, \code{multiset}). The code for 
this method is located in Appendix \ref{sec-code-validate-second}.

\subsection{Helper Classes}
\label{sec-helper-classes}
The tests presented in this section all instantiate \code{router} 
objects. Most of the tests also instantiate \code{destination} 
objects which are added to the \code{router} objects used in the 
tests. The \code{destination} objects are types derived from the 
\code{destination} base class provided as part of the GDFA. The tests 
presented here use $10$ different derived \code{destination} types.

The following tests use the first set of helper classes (defined in 
Appendix \ref{sec-code-test_classes.hpp}):

\begin{center}
\begin{tabular}{|l|l|}
\hline
Test & Sub-test\\
\hline
word\_sorter & (fall through)\\ length\_counter & (fall through)\\ 
contains\_string & (fall through)\\ contains\_letter & (fall 
through)\\ My\_default & (fall through)\\
\hline
\end{tabular}
\end{center}

The following tests use the second set of helper classes (defined in 
Appendix \ref{sec-code-test_classes_fallthrough.hpp}):

\begin{center}
\begin{tabular}{|l|l|}
\hline
Test & Sub-test\\
\hline
word\_sorter & (no fall through)\\ length\_counter & (no fall 
through)\\ contains\_striing & (no fall through)\\ contains\_letter & 
(no fall through)\\ my\_default & (no fall through)\\ 
word\_sorter\_map & (no fall through)\\ my\_default\_map & (no fall 
through)\\
\hline
\end{tabular}
\end{center}

The \code{word\_sorter} classes distribute words that begin with a 
particular letter. The \code{length\_counter} classes distribute 
words of a particular length. The \code{contains\_string} classes 
distribute words that contain a particular letter. The 
\code{contains\_letter} classes distribute words that contain a 
particular letter. The \code{my\_default} classes distribute all 
words. It is to be used as the default destination. The classes that 
are designated as ``fall through'' will always pass the element 
(word) on to the next destination handled by the router. 

The classes that are designated as ``no fall through'' will not pass 
the element (word) on to the next destination handled by the router 
if the element fits its distributing requirements. In other words, a 
``no fall through'' destination object will either distribute the 
element or pass it on the next destination object handled by the 
router, but not both. 

The classes that are designated as ``map" (such as 
\code{word\_sorter\_map} and \code{my\_default\_map}) are specialised 
versions which works with pairs. These are needed for distributing 
from an \code{std::map}.

\subsection{Test Files}
Many of the tests presented in this section perform operations on an 
input range containing \code{char}s or \code{std::string}s. The 
algorithms that are tested require access to the input range via 
\code{InputIterator}s. The following tests all require a text input 
file to be used as the source of \code{char}s and \code{std::string}s:
\begin{itemize}
\item \code{nodestinations} \item \code{noinput} \item 
\code{testreadcont} \item \code{testarray} \item 
\code{test\_inserters} \item \code{test\_char\_istream} \item 
\code{test\_string\_istream} \item \code{testrwfiles}
\end{itemize}

This file is redirected to standard input in all cases, except for 
\code{testrwfile.cpp}. In the \code{testrwfile.cpp} test, the file is 
indicated as a command-line argument. These tests are run on the text 
file \cite{dickens}.

Some of the tests presented in this section perform operations on an 
input range containing numbers. The following tests all require an 
input file of numbers to be used as a data source:
\begin{itemize}
\item \code{test\_int\_istream} \item \code{test\_double\_istream}
\end{itemize}

These files are generated by the following test helper programmes:
\begin{itemize}
\item \code{genints} \item \code{gendoubles}
\end{itemize}

These programmes are all found in Appendix \ref{sec-code-correctness}.

\subsection{Testing with Built-In Types}
\subsubsection{Test Objective}
This test is designed to check that the GDFA works properly when 
computing on an input range of type \code{char}, \code{std::string}, 
\code{int}, and \code{double}. This set is comprised of $4$ tests, 
$1$ for each type.

\subsubsection{Description of Tests}
All of the tests described in this section use an \code{std::vector} 
as the input container. Therefore, the use of a \code{std::vector} 
and its associated interator is also tested.

\paragraph{\code{char} Type Test}
In the first test, a \code{router} object operates on a range of 
\code{char}. The \code{router} is set up to sort the range of 
\code{char}s into a set of containers. There are $27$ containers: one 
for each letter of the alphabet and a default container for all other 
characters. Each of these containers is associated with a 
\code{destination} object via an iterator.

The desired output of the test is known based on the purposeful 
construction of the input range. An input range of $27000$ characters 
is generated. The range consists of $1000$ instances of each letter 
of the alphabet as well a $1000$ instances of the character `\{'. 
Once the input is generated, it is shuffled using the 
\code{std::random\_shuffle} function. Then the test is run.

After testing, each container should contain (and only contain) 
$1000$ instances of the character associated with that container. 

The validate method for this test checks the number of elements in 
each container and then makes sure that there are no misplaced 
characters. It checks for misplaced characters by iterating through 
each container to check that only the correct character is in that 
container.

The code for this test may be found in Appendix 
\ref{sec-code-test-char}.

\paragraph{\code{std::string} Type Test}
The second test uses the word sorter helper class (described in 
Section \ref{sec-helper-classes}) to sort \code{std::string}s in the 
input range based on its first character (insensitive to case).

As in the above test, the validating of this test is dependent on the 
purposeful construction of the data in the input range. An input 
range consisting of $3$-letter words (character sequences) is 
generated. The sequence consists of every $3$ letter combination of 
the letters of the $26$-character English alphabet as well as the 
non-alphabetical character `\{'. This results in $27^3$ input strings 
and $27^2$ strings beginning with each character. The generated data 
is shuffled using the \code{std::random\_shuffle} function. Then the 
test is run.

After testing, the validation test iterates through each container to 
check that each string in the container does in fact start with the 
correct letter and that each container has $27^2$ strings.

The code for this test may be found in Appendix 
\ref{sec-code-test-string}.

\paragraph{\code{int} Type Test}
The third test uses a \code{destination} called range checker. This 
\code{destination} distributes elements based on a value range. 

For this test, $10$ range checker destination objects are 
instantiated. Each checks a sub-range in the range $[0,1000000)$. The 
sub-ranges are equal in size and are constructed as follows:
\begin{itemize}
\item $(0,100000)$ \item $(100000,200000)$ \item $(200000,300000)$ 
\item $(300000,400000)$ \item $(400000,500000)$ \item 
$(500000,600000)$ \item $(600000,700000)$ \item $(700000,800000)$ 
\item $(800000,900000)$ \item $(900000,1000000)$
\end{itemize}

Like the above test, the validating of this test is dependent on the 
purposeful construction of the data in the input range. For this test 
data for the input range are generated, consisting of \code{int}s in 
the range $[0,1000000)$. The input data are shuffled using the 
\code{std::random\_shuffle} function.

Based on the construction of the destination ranges and the overall 
range of the input data, after distribution, there should be $99999$ 
elements in each range and $10$ elements that get caught by the 
default case $(0,100000,200000, \ldots , 900000)$. 

Therefore, the validate method for this test checks the size of the 
respective resultant containers. The validate method also checks the 
containers to be sure that all elements contained in them fall within 
their respective ranges. This is quickly accomplished by using the 
\code{std::min\_element} and \code{std::max\_element} functions from 
the Standard Library.

Type \code{int} works in the same way as type \code{long} and type 
\code{short}. In fact, on most computers, \code{int}s are equivalent 
either to \code{short} or to \code{long}. The range of values for an 
\code{int} is at least the same as the range for \code{short int}s 
and no larger than the range for \code{long}s. Therefore, it is 
assumed that if GDFA works properly with \code{ints}, it will also 
work properly with these other similar types.

The code for this test may be found in Appendix 
\ref{sec-code-test-int}.

\paragraph{\code{double} Type Test}
The forth test also uses a destination called range checker to 
distributes elements based on a specified value range. 

For this test, $10$ range checker destination objects are 
instantiated. Each checks a sub-range in the range $[0,1)$. The 
sub-ranges are equal in size and are constructed as follows: 
\begin{itemize}
\item $(0.0,0.1)$ \item $(0.1,0.2)$ \item $(0.2,0.3)$ \item 
$(0.3,0.4)$ \item $(0.4,0.5)$ \item $(0.5,0.6)$ \item $(0.6,0.7)$ 
\item $(0.7,0.8)$ \item $(0.8,0.9)$ \item $(0.9,1.0)$
\end{itemize}

Like the above test, validation of this test is dependent on the 
purposeful construction of the data in the input range. For this test 
data for the input range is generated, consisting of integers in the 
range $[0,1)$. The input range is constructed starting with $0.0$. 
Each subsequent value is incremented by $0.000001$. The input data is 
shuffled using the \code{std::random\_shuffle} function.

Based on the construction of the destination ranges and the overall 
range of the input data, after distribution, there should be $99999$ 
elements in each range and $10$ elements that get caught by the 
default case $(0.0, 0.1, 0.2, \ldots , 0.9)$.

Therefore, the validate method for this test checks the size of the 
respective resultant containers. The validate method also checks the 
containers to be sure that all elements contained in them fall within 
their respective ranges. This is quickly accomplished by using the 
\code{std::min\_element} and \code{std::max\_element} functions from 
the Standard Library.

Type \code{double} functions in the same way as type \code{float} 
(although the range and precision differ). Therefore, it is assumed 
that if GDFA works properly with type \code{double}, it will also 
work properly with type \code{float}.

Note that floating point accuracy causes inconsistencies in the 
comparison of elements of type \code{double}. Therefore, the input 
generator, \code{destination}s, and \code{validate} method make use 
of a variable \code{epsilon} which is the precision that we use for 
distribution and validation purposes. Specifically, two 
\code{double}s, \code{one} and \code{two}, are considered to be the 
``equal'' if \code{abs(one - two)<epsilon}. A class was created to 
facilitate the comparison based on this predetermined level of 
precision. This class was necessary to assure correct filtering. It 
is incumbent on the user to instill floating point precision 
comparison consistency.

The code for this test may be found in Appendix 
\ref{sec-code-test-double}.

\subsubsection{Results}
The following are outputs from the respective test programmes; each 
indicates that the GDFA Library passes the test in question.

\paragraph{\code{test\_char.hpp} Output}
\begin{flushleft} \small \label{part72}
\colorbox{light}{$\langle$output from test\_char.hpp {\footnotesize \hypertarget{79a}{79a}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@Test:  test_char.cpp@\\
\mbox{}\verb@@\\
\mbox{}\verb@Test Using type char as input.@\\
\mbox{}\verb@***********************************@\\
\mbox{}\verb@@\\
\mbox{}\verb@Results:@\\
\mbox{}\verb@@\\
\mbox{}\verb@a: 1000@\\
\mbox{}\verb@b: 1000@\\
\mbox{}\verb@c: 1000@\\
\mbox{}\verb@d: 1000@\\
\mbox{}\verb@e: 1000@\\
\mbox{}\verb@f: 1000@\\
\mbox{}\verb@g: 1000@\\
\mbox{}\verb@h: 1000@\\
\mbox{}\verb@i: 1000@\\
\mbox{}\verb@j: 1000@\\
\mbox{}\verb@k: 1000@\\
\mbox{}\verb@l: 1000@\\
\mbox{}\verb@m: 1000@\\
\mbox{}\verb@n: 1000@\\
\mbox{}\verb@o: 1000@\\
\mbox{}\verb@p: 1000@\\
\mbox{}\verb@q: 1000@\\
\mbox{}\verb@r: 1000@\\
\mbox{}\verb@s: 1000@\\
\mbox{}\verb@t: 1000@\\
\mbox{}\verb@u: 1000@\\
\mbox{}\verb@v: 1000@\\
\mbox{}\verb@w: 1000@\\
\mbox{}\verb@x: 1000@\\
\mbox{}\verb@y: 1000@\\
\mbox{}\verb@z: 1000@\\
\mbox{}\verb@Number of elements caught by default case: 1000@\\
\mbox{}\verb@Passed Validation Test@\\
\mbox{}\verb@@\\
\mbox{}\verb@*************     END OF RESULTS     *************@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Not used.
\end{list}
\end{flushleft}
\paragraph{\code{test\_string.cpp} Output}
\begin{flushleft} \small \label{part73}
\colorbox{light}{$\langle$output from test\_string.cpp {\footnotesize \hypertarget{79b}{79b}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@Test:  test_string.cpp@\\
\mbox{}\verb@@\\
\mbox{}\verb@Test Using strings as input.@\\
\mbox{}\verb@***********************************@\\
\mbox{}\verb@@\\
\mbox{}\verb@Results:@\\
\mbox{}\verb@@\\
\mbox{}\verb@a: 729@\\
\mbox{}\verb@b: 729@\\
\mbox{}\verb@c: 729@\\
\mbox{}\verb@d: 729@\\
\mbox{}\verb@e: 729@\\
\mbox{}\verb@f: 729@\\
\mbox{}\verb@g: 729@\\
\mbox{}\verb@h: 729@\\
\mbox{}\verb@i: 729@\\
\mbox{}\verb@j: 729@\\
\mbox{}\verb@k: 729@\\
\mbox{}\verb@l: 729@\\
\mbox{}\verb@m: 729@\\
\mbox{}\verb@n: 729@\\
\mbox{}\verb@o: 729@\\
\mbox{}\verb@p: 729@\\
\mbox{}\verb@q: 729@\\
\mbox{}\verb@r: 729@\\
\mbox{}\verb@s: 729@\\
\mbox{}\verb@t: 729@\\
\mbox{}\verb@u: 729@\\
\mbox{}\verb@v: 729@\\
\mbox{}\verb@w: 729@\\
\mbox{}\verb@x: 729@\\
\mbox{}\verb@y: 729@\\
\mbox{}\verb@z: 729@\\
\mbox{}\verb@Number of elements caught by default case: 729@\\
\mbox{}\verb@Passed Validation Test@\\
\mbox{}\verb@@\\
\mbox{}\verb@*************     END OF RESULTS     *************@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Not used.
\end{list}
\end{flushleft}
\paragraph{\code{test\_int.cpp} Output}
\begin{flushleft} \small \label{part74}
\colorbox{light}{$\langle$output from test\_int.cpp {\footnotesize \hypertarget{80}{80}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@Test:  test_int.cpp@\\
\mbox{}\verb@@\\
\mbox{}\verb@Test Using integers as input.@\\
\mbox{}\verb@***********************************@\\
\mbox{}\verb@@\\
\mbox{}\verb@Results:@\\
\mbox{}\verb@@\\
\mbox{}\verb@number of elements in each range, with the max and min element in the ranges@\\
\mbox{}\verb@(0,100000): 99999 99999 1@\\
\mbox{}\verb@(100000,200000): 99999 199999 100001@\\
\mbox{}\verb@(200000,300000): 99999 299999 200001@\\
\mbox{}\verb@(300000,400000): 99999 399999 300001@\\
\mbox{}\verb@(400000,500000): 99999 499999 400001@\\
\mbox{}\verb@(500000,600000): 99999 599999 500001@\\
\mbox{}\verb@(600000,700000): 99999 699999 600001@\\
\mbox{}\verb@(700000,800000): 99999 799999 700001@\\
\mbox{}\verb@(800000,900000): 99999 899999 800001@\\
\mbox{}\verb@(900000,1000000): 99999 999999 900001@\\
\mbox{}\verb@Number elements caught by default case: 10@\\
\mbox{}\verb@Passed Validation Test@\\
\mbox{}\verb@@\\
\mbox{}\verb@*************     END OF RESULTS     *************@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Not used.
\end{list}
\end{flushleft}
\paragraph{\code{test\_double.cpp} Output}
\begin{flushleft} \small \label{part75}
\colorbox{light}{$\langle$output from test\_double.cpp {\footnotesize \hypertarget{81}{81}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@Test:  test_double.cpp@\\
\mbox{}\verb@@\\
\mbox{}\verb@Test Using type double as input.@\\
\mbox{}\verb@***********************************@\\
\mbox{}\verb@@\\
\mbox{}\verb@Results:@\\
\mbox{}\verb@@\\
\mbox{}\verb@number of elements in each range, with the max and min element in the ranges@\\
\mbox{}\verb@(0,0.1)  : 99999 0.099999 1e-06@\\
\mbox{}\verb@(0.1,0.2): 99999 0.199999 0.100001@\\
\mbox{}\verb@(0.2,0.3): 99999 0.299999 0.200001@\\
\mbox{}\verb@(0.3,0.4): 99999 0.399999 0.300001@\\
\mbox{}\verb@(0.4,0.5): 99999 0.499999 0.400001@\\
\mbox{}\verb@(0.5,0.6): 99999 0.599999 0.500001@\\
\mbox{}\verb@(0.6,0.7): 99999 0.699999 0.600001@\\
\mbox{}\verb@(0.7,0.8): 99999 0.799999 0.700001@\\
\mbox{}\verb@(0.8,0.9): 99999 0.899999 0.800001@\\
\mbox{}\verb@(0.9,1)  : 99999 0.999999 0.900001@\\
\mbox{}\verb@Number of elements caught by default case: 10@\\
\mbox{}\verb@Passed Validation Test@\\
\mbox{}\verb@@\\
\mbox{}\verb@*************     END OF RESULTS     *************@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Not used.
\end{list}
\end{flushleft}
\subsection{Testing of Priorities}
\subsubsection{Test Objective}
This set of tests validates that the GDFA priority levels function 
properly.

\subsubsection{Description}
This test validates the use priorities in the GDFA library. GDFA 
allows the use of 4 priority levels. The priority levels determine 
the order in which an element is passed to the \code{router}'s 
\code{destination} objects. 

This test set runs configurations of $2$, $3$, and $4$ priorities. 

For a given test with $N$ priority levels, a \code{router} is created 
with a set of associated \code{destination}s. The \code{destination}s 
are assigned \code{N} different priority levels. For example, the 
$4$-priority test is set up by creating a \code{router} with multiple 
\code{destination}s where at least one \code{destination} is assigned 
an \code{urgent\_priority}, one is assigned an \code{high\_priority}, 
one is assigned to \code{normal\_priority} and the fourth assigned to 
\code{low\_priority}. There are $4$ different types of 
\code{destination} classes used in the $4$-priority test. These 
\code{destination} types are \code{contains\_string}, 
\code{contains\_letter}, \code{length\_counter}, and 
\code{word\_sorter}. Multiple instances of each \code{destination} 
type are used. For example, there are $2$ \code{length\_counter} 
\code{destination}s and $26$ \code{word\_sorter} \code{destination}s, 
$1$ \code{contains\_letter} \code{destination}, and $1$ 
\code{contains\_string} \code{destination} used in the $4$-priority 
example. This setup is useful in testing the priorities because the 
\code{destination} types are not mutually exclusive. In other words, 
one element may meet the requirements of more than one 
\code{destination}. Consequently, priority matters, because the order 
in which an element is passed to a \code{destination} affects the 
results of the distribution.	

The test is performed on this \code{router} by creating the needed 
input and storing it a storage \code{std::vector} for use with this 
test. The \code{router.distribute()} member function is then run on 
the data, and the results are printed and stored for validation.

Validation of the test results is done by a validate function which 
checks the contents of each resulting container. The input data 
generated for this test is constructed such that we know the expected 
results. The requirements of the data for the various destinations 
overlap. The construction of the data intentionally creates a 
scenario where the expected results require proper ordering of the 
destinations based on priority. 

The input data for the $4$-priority test is constructed as follows:

$81$ strings containing the sub-string "ea" are generated Of those, 
27*2 with `e' as first letter and $27$ with ``ea'' as the last $2$ 
letters for a total of $81$.

$4267$ strings containing the string ``a'' are generated. Of those, 
27*27*3 begin with “a” and 26*27*2 have “a” as the second letter.

There are $26$ other characters (`a' through `z' and `\{'), each of 
which begin strings, and among those each has $27*2$ strings that 
have `a' as the second character) and $26^2$ have `a' as the third 
letter for a total of $4267$ (there are $26^2$ strings with the third 
character being `a' that do not have an `a' as the first or second 
character)

\begin{center}
\begin{tabular}{|p{5in}|}
\hline
there are $19683$ strings of length $1$ ($27^3$)\\ there are $19683$ 
strings of length $2$ ($27^3$)\\ there are $2187$ strings beginning 
with each letter (`a'-`z') ($27^2*3$)\\ there are $2187$ strings 
beginning with a nonletter ($27^2*3$)\\ there are $59049$ strings 
total ($27^3*3$)\\
\hline
\end{tabular}
\end{center}

Therefore, the expected results (in the nofallthrough test) are:

\begin{center}
\begin{tabular}{|p{5in}|}
\hline
$81$ strings with ``ea''\\ $4186$ strings with ``a'' ($4267-81$)\\ 
$18954$ strings of length $1$ ($19683-27^2$ (one letter strings of 
``a''))\\ $18252$ strings of length $2$\\ ($19683-27^2$ ($2$-letter 
strings beginning with ``a'') - $26*27$ ($2$-letter strings not 
beginning with ``a'' but ending with ``a''))\\ $676$ strings 
beginning with anything but ``a''\\
\hline
\end{tabular}
\end{center}

The validation method tests the actual results with these expected 
results.

The same data set is used for the $2$- and $3$-priority tests. The 
expected results for these tests are different. Therefore, a separate 
validate method is constructed to test those results.

This test is also run in the ``no fall through'' configuration for 
the \mbox{$2$-,} \mbox{$3$-,} and \mbox{$4$-priority} configurations. 
These configurations are run using the same input data set. The 
expected results for these tests are different. Therefore, a separate 
validate method is constructed to test those results.

Each of the above tests is run for every combination of priority 
levels that comport with the above ordering. For example, if there 
are $2$ priority levels, the levels could be: 

\begin{center}
\begin{tabular}{|l|l|}
\hline
Destination A & Destination B\\
\hline
urgent & normal\\ urgent & low\\ high & normal\\ high & low\\ normal 
& low\\
\hline
\end{tabular}
\end{center}

These $2$-priority configurations are logically the same. Therefore, 
the test validates that all configurations produce the same desired 
output.

\subsubsection{Results}
The following are outputs from the respective test programmes; each 
indicates that the GDFA Library passes the test in question.

\paragraph{\code{priority2\_fallthrough.cpp} Output}
The code implementing this test can be found in Appendix 
\ref{sec-code-test-2pt-f}.

\begin{flushleft} \small \label{part76}
\colorbox{light}{$\langle$output from priority2\_fallthrough.cpp {\footnotesize \hypertarget{83}{83}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@Test:  priority2_fallthrough.cpp@\\
\mbox{}\verb@@\\
\mbox{}\verb@Test router with 2 priorities (allowing fall through)@\\
\mbox{}\verb@***********************************************************@\\
\mbox{}\verb@@\\
\mbox{}\verb@Note: Fall through means that a destination@\\
\mbox{}\verb@passes the element on to the next destination.@\\
\mbox{}\verb@@\\
\mbox{}\verb@**********************************************@\\
\mbox{}\verb@@\\
\mbox{}\verb@Results:@\\
\mbox{}\verb@@\\
\mbox{}\verb@results of testing urgent priority and high priority@\\
\mbox{}\verb@words of length 1: 19683@\\
\mbox{}\verb@words of length 2: 19683@\\
\mbox{}\verb@counts for all other words, based on starting character (case insensitive)@\\
\mbox{}\verb@a: 2187@\\
\mbox{}\verb@b: 2187@\\
\mbox{}\verb@c: 2187@\\
\mbox{}\verb@d: 2187@\\
\mbox{}\verb@e: 2187@\\
\mbox{}\verb@f: 2187@\\
\mbox{}\verb@g: 2187@\\
\mbox{}\verb@h: 2187@\\
\mbox{}\verb@i: 2187@\\
\mbox{}\verb@j: 2187@\\
\mbox{}\verb@k: 2187@\\
\mbox{}\verb@l: 2187@\\
\mbox{}\verb@m: 2187@\\
\mbox{}\verb@n: 2187@\\
\mbox{}\verb@o: 2187@\\
\mbox{}\verb@p: 2187@\\
\mbox{}\verb@q: 2187@\\
\mbox{}\verb@r: 2187@\\
\mbox{}\verb@s: 2187@\\
\mbox{}\verb@t: 2187@\\
\mbox{}\verb@u: 2187@\\
\mbox{}\verb@v: 2187@\\
\mbox{}\verb@w: 2187@\\
\mbox{}\verb@x: 2187@\\
\mbox{}\verb@y: 2187@\\
\mbox{}\verb@z: 2187@\\
\mbox{}\verb@Default: 59049@\\
\mbox{}\verb@Passed test for urgent and high priorities@\\
\mbox{}\verb@Testing Urgent and normal priority@\\
\mbox{}\verb@Passed test for urgent and normal priority@\\
\mbox{}\verb@Testing Urgent and low priority@\\
\mbox{}\verb@Passed test for urgent and low priority@\\
\mbox{}\verb@Testing high and normal priority@\\
\mbox{}\verb@Passed test for high and normal priority@\\
\mbox{}\verb@Testing high and low priority@\\
\mbox{}\verb@Passed test for high and low priority@\\
\mbox{}\verb@Testing normal and low priority@\\
\mbox{}\verb@Passed test for normal and low priority@\\
\mbox{}\verb@@\\
\mbox{}\verb@*************     END OF RESULTS     *************@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Not used.
\end{list}
\end{flushleft}
\paragraph{\code{priority2\_nofallthrough.cpp} Output}
The code implementing this test can be found in Appendix 
\ref{sec-code-test-2pt-n}.

\begin{flushleft} \small \label{part77}
\colorbox{light}{$\langle$output from priority2\_nofallthrough.cpp {\footnotesize \hypertarget{85}{85}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@Test:  priority2_nofallthrough.cpp@\\
\mbox{}\verb@@\\
\mbox{}\verb@Test router with 2 priorities (No fall through)@\\
\mbox{}\verb@***********************************************@\\
\mbox{}\verb@@\\
\mbox{}\verb@(Note: Fall through means that a destination@\\
\mbox{}\verb@passes the element on to the next destination.@\\
\mbox{}\verb@@\\
\mbox{}\verb@**********************************************@\\
\mbox{}\verb@@\\
\mbox{}\verb@Results:@\\
\mbox{}\verb@@\\
\mbox{}\verb@results of testing urgent priority and high priority@\\
\mbox{}\verb@words of length 1: 19683@\\
\mbox{}\verb@words of length 2: 19683@\\
\mbox{}\verb@counts for all other words, based on starting character (case insensitive)@\\
\mbox{}\verb@a: 729@\\
\mbox{}\verb@b: 729@\\
\mbox{}\verb@c: 729@\\
\mbox{}\verb@d: 729@\\
\mbox{}\verb@e: 729@\\
\mbox{}\verb@f: 729@\\
\mbox{}\verb@g: 729@\\
\mbox{}\verb@h: 729@\\
\mbox{}\verb@i: 729@\\
\mbox{}\verb@j: 729@\\
\mbox{}\verb@k: 729@\\
\mbox{}\verb@l: 729@\\
\mbox{}\verb@m: 729@\\
\mbox{}\verb@n: 729@\\
\mbox{}\verb@o: 729@\\
\mbox{}\verb@p: 729@\\
\mbox{}\verb@q: 729@\\
\mbox{}\verb@r: 729@\\
\mbox{}\verb@s: 729@\\
\mbox{}\verb@t: 729@\\
\mbox{}\verb@u: 729@\\
\mbox{}\verb@v: 729@\\
\mbox{}\verb@w: 729@\\
\mbox{}\verb@x: 729@\\
\mbox{}\verb@y: 729@\\
\mbox{}\verb@z: 729@\\
\mbox{}\verb@Default: 729@\\
\mbox{}\verb@Passed test for urgent and high priorities@\\
\mbox{}\verb@Testing Urgent and normal priority@\\
\mbox{}\verb@Passed test for urgent and normal priority@\\
\mbox{}\verb@Testing Urgent and low priority@\\
\mbox{}\verb@Passed test for urgent and low priority@\\
\mbox{}\verb@Testing high and normal priority@\\
\mbox{}\verb@Passed test for high and normal priority@\\
\mbox{}\verb@Testing high and low priority@\\
\mbox{}\verb@Passed test for high and low priority@\\
\mbox{}\verb@Testing normal and low priority@\\
\mbox{}\verb@Passed test for normal and low priority@\\
\mbox{}\verb@@\\
\mbox{}\verb@*************     END OF RESULTS     *************@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Not used.
\end{list}
\end{flushleft}
\paragraph{\code{priority3\_fallthrough.cpp} Output}
The code implementing this test can be found in Appendix 
\ref{sec-code-test-3pt-f}.

\begin{flushleft} \small \label{part78}
\colorbox{light}{$\langle$output from priority3\_fallthrough.cpp {\footnotesize \hypertarget{86}{86}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@Test:  priority3_fallthrough.cpp@\\
\mbox{}\verb@@\\
\mbox{}\verb@Test router with 3 priorities (allowing fall through)@\\
\mbox{}\verb@***********************************************************@\\
\mbox{}\verb@@\\
\mbox{}\verb@Note: Fall through means that a destination@\\
\mbox{}\verb@passes the element on to the next destination.@\\
\mbox{}\verb@@\\
\mbox{}\verb@**********************************************@\\
\mbox{}\verb@@\\
\mbox{}\verb@Results:@\\
\mbox{}\verb@@\\
\mbox{}\verb@Results of testing urgent, high and normal priorities@\\
\mbox{}\verb@words containing the letter (lowercase) a: 4267@\\
\mbox{}\verb@words of length 1: 19683@\\
\mbox{}\verb@words of length 2: 19683@\\
\mbox{}\verb@counts for all other words, based on starting character, case insensitive@\\
\mbox{}\verb@a: 2187@\\
\mbox{}\verb@b: 2187@\\
\mbox{}\verb@c: 2187@\\
\mbox{}\verb@d: 2187@\\
\mbox{}\verb@e: 2187@\\
\mbox{}\verb@f: 2187@\\
\mbox{}\verb@g: 2187@\\
\mbox{}\verb@h: 2187@\\
\mbox{}\verb@i: 2187@\\
\mbox{}\verb@j: 2187@\\
\mbox{}\verb@k: 2187@\\
\mbox{}\verb@l: 2187@\\
\mbox{}\verb@m: 2187@\\
\mbox{}\verb@n: 2187@\\
\mbox{}\verb@o: 2187@\\
\mbox{}\verb@p: 2187@\\
\mbox{}\verb@q: 2187@\\
\mbox{}\verb@r: 2187@\\
\mbox{}\verb@s: 2187@\\
\mbox{}\verb@t: 2187@\\
\mbox{}\verb@u: 2187@\\
\mbox{}\verb@v: 2187@\\
\mbox{}\verb@w: 2187@\\
\mbox{}\verb@x: 2187@\\
\mbox{}\verb@y: 2187@\\
\mbox{}\verb@z: 2187@\\
\mbox{}\verb@Default: 59049@\\
\mbox{}\verb@Passed test for urgent, high and normal priorities@\\
\mbox{}\verb@Testing urgent, high and low priority@\\
\mbox{}\verb@Passed test for urgent, high and low priority@\\
\mbox{}\verb@Testing urgent, normal and low priority@\\
\mbox{}\verb@Passed test for urgent, normal and low priority@\\
\mbox{}\verb@Testing high, normal and low priority@\\
\mbox{}\verb@Passed test for high, normal and low priority@\\
\mbox{}\verb@@\\
\mbox{}\verb@*************     END OF RESULTS     *************@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Not used.
\end{list}
\end{flushleft}
\paragraph{\code{priority3\_nofallthrough.cpp} Output}
The code implementing this test can be found in Appendix 
\ref{sec-code-test-3pt-n}.

\begin{flushleft} \small \label{part79}
\colorbox{light}{$\langle$output from priority3\_nofallthrough.cpp {\footnotesize \hypertarget{87}{87}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@Test:  priority3_nofallthrough.cpp@\\
\mbox{}\verb@@\\
\mbox{}\verb@Test router with 3 priorities (No fall through)@\\
\mbox{}\verb@***********************************************@\\
\mbox{}\verb@@\\
\mbox{}\verb@(Note: Fall through means that a destination@\\
\mbox{}\verb@passes the element on to the next destination.@\\
\mbox{}\verb@@\\
\mbox{}\verb@**********************************************@\\
\mbox{}\verb@@\\
\mbox{}\verb@Results:@\\
\mbox{}\verb@@\\
\mbox{}\verb@Results of testing urgent, high and normal priorities@\\
\mbox{}\verb@words containing the letter (lowercase) a: 4267@\\
\mbox{}\verb@words of length 1: 18954@\\
\mbox{}\verb@words of length 2: 18252@\\
\mbox{}\verb@counts for all other words, based on starting character, case insensitive@\\
\mbox{}\verb@a: 0@\\
\mbox{}\verb@b: 676@\\
\mbox{}\verb@c: 676@\\
\mbox{}\verb@d: 676@\\
\mbox{}\verb@e: 676@\\
\mbox{}\verb@f: 676@\\
\mbox{}\verb@g: 676@\\
\mbox{}\verb@h: 676@\\
\mbox{}\verb@i: 676@\\
\mbox{}\verb@j: 676@\\
\mbox{}\verb@k: 676@\\
\mbox{}\verb@l: 676@\\
\mbox{}\verb@m: 676@\\
\mbox{}\verb@n: 676@\\
\mbox{}\verb@o: 676@\\
\mbox{}\verb@p: 676@\\
\mbox{}\verb@q: 676@\\
\mbox{}\verb@r: 676@\\
\mbox{}\verb@s: 676@\\
\mbox{}\verb@t: 676@\\
\mbox{}\verb@u: 676@\\
\mbox{}\verb@v: 676@\\
\mbox{}\verb@w: 676@\\
\mbox{}\verb@x: 676@\\
\mbox{}\verb@y: 676@\\
\mbox{}\verb@z: 676@\\
\mbox{}\verb@Default: 676@\\
\mbox{}\verb@Passed test for urgent, high and normal priorities@\\
\mbox{}\verb@Testing urgent, high and low priority@\\
\mbox{}\verb@Passed test for urgent high and low priority@\\
\mbox{}\verb@Testing urgent, normal and low priority@\\
\mbox{}\verb@Passed test for urgent, normal and low priority@\\
\mbox{}\verb@Testing high, normal and low priority@\\
\mbox{}\verb@Passed test for high, normal and low priority@\\
\mbox{}\verb@@\\
\mbox{}\verb@*************     END OF RESULTS     *************@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Not used.
\end{list}
\end{flushleft}
\paragraph{\code{priority4\_fallthrough.cpp} Output}
The code implementing this test can be found in Appendix 
\ref{sec-code-test-4pt-f}.

\begin{flushleft} \small \label{part80}
\colorbox{light}{$\langle$output from priority4\_fallthrough.cpp {\footnotesize \hypertarget{88}{88}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@Test:  priority4_fallthrough.cpp@\\
\mbox{}\verb@@\\
\mbox{}\verb@Test router with 4 priorities (allowing fall through)@\\
\mbox{}\verb@***********************************************************@\\
\mbox{}\verb@@\\
\mbox{}\verb@Note: Fall through means that a destination@\\
\mbox{}\verb@passes the element on to the next destination.@\\
\mbox{}\verb@@\\
\mbox{}\verb@**********************************************@\\
\mbox{}\verb@@\\
\mbox{}\verb@Results:@\\
\mbox{}\verb@@\\
\mbox{}\verb@Results of testing urgent, high, normal and low priorities@\\
\mbox{}\verb@Words containing the string "ea": 81@\\
\mbox{}\verb@words containing the letter (lowercase) a: 4267@\\
\mbox{}\verb@words of length 1: 19683@\\
\mbox{}\verb@words of length 2: 19683@\\
\mbox{}\verb@counts for all other words, based on starting character, case insensitive@\\
\mbox{}\verb@a: 2187@\\
\mbox{}\verb@b: 2187@\\
\mbox{}\verb@c: 2187@\\
\mbox{}\verb@d: 2187@\\
\mbox{}\verb@e: 2187@\\
\mbox{}\verb@f: 2187@\\
\mbox{}\verb@g: 2187@\\
\mbox{}\verb@h: 2187@\\
\mbox{}\verb@i: 2187@\\
\mbox{}\verb@j: 2187@\\
\mbox{}\verb@k: 2187@\\
\mbox{}\verb@l: 2187@\\
\mbox{}\verb@m: 2187@\\
\mbox{}\verb@n: 2187@\\
\mbox{}\verb@o: 2187@\\
\mbox{}\verb@p: 2187@\\
\mbox{}\verb@q: 2187@\\
\mbox{}\verb@r: 2187@\\
\mbox{}\verb@s: 2187@\\
\mbox{}\verb@t: 2187@\\
\mbox{}\verb@u: 2187@\\
\mbox{}\verb@v: 2187@\\
\mbox{}\verb@w: 2187@\\
\mbox{}\verb@x: 2187@\\
\mbox{}\verb@y: 2187@\\
\mbox{}\verb@z: 2187@\\
\mbox{}\verb@Default: 59049@\\
\mbox{}\verb@Passed Validation Test@\\
\mbox{}\verb@@\\
\mbox{}\verb@*************     END OF RESULTS     *************@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Not used.
\end{list}
\end{flushleft}
\paragraph{\code{priority4\_nofallthrough.cpp} Output}
The code implementing this test can be found in Appendix 
\ref{sec-code-test-4pt-n}.

\begin{flushleft} \small \label{part81}
\colorbox{light}{$\langle$output from priority4\_nofallthrough.cpp {\footnotesize \hypertarget{89}{89}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@Test:  priority4_nofallthrough.cpp@\\
\mbox{}\verb@@\\
\mbox{}\verb@Test router with 4 priorities (No fall through)@\\
\mbox{}\verb@***********************************************@\\
\mbox{}\verb@@\\
\mbox{}\verb@(Note: Fall through means that a destination@\\
\mbox{}\verb@passes the element on to the next destination.@\\
\mbox{}\verb@@\\
\mbox{}\verb@**********************************************@\\
\mbox{}\verb@@\\
\mbox{}\verb@Results:@\\
\mbox{}\verb@@\\
\mbox{}\verb@Results of testing urgent, high, normal and low priorities@\\
\mbox{}\verb@Words containing the string "ea": 81@\\
\mbox{}\verb@words containing the letter (lowercase) a: 4186@\\
\mbox{}\verb@words of length 1: 18954@\\
\mbox{}\verb@words of length 2: 18252@\\
\mbox{}\verb@counts for all other words, based on starting character, case insensitive@\\
\mbox{}\verb@a: 0@\\
\mbox{}\verb@b: 676@\\
\mbox{}\verb@c: 676@\\
\mbox{}\verb@d: 676@\\
\mbox{}\verb@e: 676@\\
\mbox{}\verb@f: 676@\\
\mbox{}\verb@g: 676@\\
\mbox{}\verb@h: 676@\\
\mbox{}\verb@i: 676@\\
\mbox{}\verb@j: 676@\\
\mbox{}\verb@k: 676@\\
\mbox{}\verb@l: 676@\\
\mbox{}\verb@m: 676@\\
\mbox{}\verb@n: 676@\\
\mbox{}\verb@o: 676@\\
\mbox{}\verb@p: 676@\\
\mbox{}\verb@q: 676@\\
\mbox{}\verb@r: 676@\\
\mbox{}\verb@s: 676@\\
\mbox{}\verb@t: 676@\\
\mbox{}\verb@u: 676@\\
\mbox{}\verb@v: 676@\\
\mbox{}\verb@w: 676@\\
\mbox{}\verb@x: 676@\\
\mbox{}\verb@y: 676@\\
\mbox{}\verb@z: 676@\\
\mbox{}\verb@Default: 676@\\
\mbox{}\verb@Passed Validation Test@\\
\mbox{}\verb@@\\
\mbox{}\verb@*************     END OF RESULTS     *************@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Not used.
\end{list}
\end{flushleft}
\subsection{Insert Iterator Tests}
\subsubsection{Test Objective}
This set of tests is intended to validate that the GDFA work properly 
with all of the various front- and back-insertion iterators as the 
\code{OutputIterator} of a \code{destination} class.

\subsubsection{Description}
This test validates the use of the types generated by the following 
types, as the \code{OutputIterator} of a the \code{destination} 
objects:

\begin{itemize}
\item \code{std::front\_insert\_iterator(std::deque)} \item 
\code{std::front\_insert\_iterator(std::list)} \item 
\code{std::back\_insert\_iterator(std::deque)} \item 
\code{std::back\_insert\_iterator(std::list)} \item 
\code{std::back\_insert\_iterator(std::vector)}
\end{itemize}

The testing procedure works as follows:

First we use the \code{word\_sorter} class to construct a 
\code{router} with $27$ \code{destination}s that output to an 
\code{std::vector} via an iterator. 

Second, we perform a baseline test using 
\code{std::back\_insert\_iterator(std::vector)} to define the input 
range. The input element type is \code{std::string}.

Third, we perform the above sequence using the types to be tested as 
the location that the \code{destination} class outputs to.

Then we validate each test by comparing the results to the results of 
the baseline test. Due to the fact that all of the containers are 
sequential we can validate the results of the tests by explicitly 
comparing the results to determine if they are identical. If the 
results are identical to the baseline test, the test passes. 
Otherwise, the test is failed.

The \code{validate} method for the front-insertion sequences is 
slightly different. Since the baseline is a back-insertion sequence, 
the results (the distributed sequence elements produced by the call 
to \code{router.distribute()}) of the tests using the front-insertion 
sequences will differ because we are pushing onto the front of the 
container instead of the back. Consequently, the resulting sequences 
will be in the reverse order of the 
\code{std::back\_insert\_iterator(std::vector)}. The code 
implementing this test may be found in Appendix 
\ref{sec-code-test-insert-iter}.

\subsubsection{Results}
The following is the output from the test programme; it indicates 
that the GDFA Library passes these tests.

\begin{flushleft} \small \label{part82}
\colorbox{light}{$\langle$output of testinserters.cpp {\footnotesize \hypertarget{91}{91}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@testinserters.cpp@\\
\mbox{}\verb@@\\
\mbox{}\verb@Test of Reading from Standard Library Containers@\\
\mbox{}\verb@using front or back inserters (where applicable).@\\
\mbox{}\verb@*************************************************@\\
\mbox{}\verb@@\\
\mbox{}\verb@Results:@\\
\mbox{}\verb@@\\
\mbox{}\verb@Results for filtering into vector using a back insert iterator.  Will be used for testing other insert iterators@\\
\mbox{}\verb@Number of words beginning with each letter, case insensitive:@\\
\mbox{}\verb@a: 3228@\\
\mbox{}\verb@b: 1417@\\
\mbox{}\verb@c: 1255@\\
\mbox{}\verb@d: 894@\\
\mbox{}\verb@e: 532@\\
\mbox{}\verb@f: 1020@\\
\mbox{}\verb@g: 661@\\
\mbox{}\verb@h: 2394@\\
\mbox{}\verb@i: 2020@\\
\mbox{}\verb@j: 94@\\
\mbox{}\verb@k: 200@\\
\mbox{}\verb@l: 740@\\
\mbox{}\verb@m: 1080@\\
\mbox{}\verb@n: 639@\\
\mbox{}\verb@o: 1653@\\
\mbox{}\verb@p: 813@\\
\mbox{}\verb@q: 64@\\
\mbox{}\verb@r: 544@\\
\mbox{}\verb@s: 2365@\\
\mbox{}\verb@t: 4282@\\
\mbox{}\verb@u: 396@\\
\mbox{}\verb@v: 163@\\
\mbox{}\verb@w: 2108@\\
\mbox{}\verb@x: 1@\\
\mbox{}\verb@y: 460@\\
\mbox{}\verb@z: 2@\\
\mbox{}\verb@Default: 823@\\
\mbox{}\verb@@\\
\mbox{}\verb@Testing back insert iterator deque@\\
\mbox{}\verb@Passed test for back insert iterator deque@\\
\mbox{}\verb@Testing back insert iterator list@\\
\mbox{}\verb@Passed test for back insert iterator list@\\
\mbox{}\verb@Testing front insert iterator deque@\\
\mbox{}\verb@Passed test for front insert iterator deque@\\
\mbox{}\verb@Testing front insert iterator list@\\
\mbox{}\verb@Passed test for front insert iterator list@\\
\mbox{}\verb@@\\
\mbox{}\verb@*************     END OF RESULTS     *************@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Not used.
\end{list}
\end{flushleft}
\subsection{Reading from Standard Library Containers Tests}
\subsubsection{Test Objective}
This set of tests is intended to validate that the GDFA work properly 
with all of the Standard Library container classes via their 
associated input iterators.

\subsubsection{Description of Tests}
In this set of tests, the following Standard Library containers are 
used to hold the range of elements operated on by the \code{router} 
object:

\begin{itemize}
\item \code{std::list} \item \code{std::deque} \item 
\code{std::multiset} \item \code{std::map}
\end{itemize}


The tests in Section \ref{sec-priority-tests} use an 
\code{std::vector} as the input container. Therefore, it is not 
necessary to re-test the use of that container.

All of these tests use the \code{word\_sorter} derived destination 
class to sort strings in the input range based on its first character 
(insensitive to case).

To administer these tests we first read all the input into an 
\code{std::vector} for use later. This is used to store the 
unadulterated data set to be used (insert into) to test the 
\code{std::list}, \code{std::deque}, \code{std::multiset} and 
\code{std::map}. We then establish a baseline test by distributing 
the data using our established \code{router} object. We assume, based 
on previous tests, that the GDFA work correctly with an 
\code{std::vector}. We then test \code{list}, \code{deque}, 
\code{std::multiset}, and \code{std::map} by validating that the 
results are match the results obtained in our baseline test.

An \code{std::multiset} (but not an \code{std::set}) is used because, 
for any given set of input strings, a given string can occur multiple 
times. Therefore, an \code{std::multiset} ensures that all of the 
recurrent strings are accounted for. An \code{std::set} cannot be 
used with the GDFA on arbitrary input.

An \code{std::map} (rather than a \code{std::multimap}) can be used 
with GDFA if constructed properly. The type 
\code{std::map<std::string,int>} is used. The \code{std::map} stores 
\code{std::pair}s of \code{<std::string,int>}. The \code{std::string} 
itself is used as the key. The second member of the \code{std::pair} 
keeps track of the number of instances of each unique string.

The results of the test run using \code{std::multiset} and 
\code{std::map} ``matches'' the baseline test. However, due to the 
associative nature of these containers the results will not be 
identical to the results of the baseline test. However the number of 
words beginning with each letter will be the same as in the baseline 
test. Therefore, the \code{validate} method used for these containers 
will accept if the number of elements in each resulting container 
matches the number of elements in the respective containers obtained 
from the baseline test. A separate \code{validate} method was created 
to test \code{std::multiset} and \code{std::map}. The 
\code{std::multiset} \code{validate} method works with individual 
elements and the \code{std::map} \code{validate} method works with 
\code{std::pairs} where the second member of the \code{std::pair} is 
the number of instances of the unique \code{std::string} stored in 
the \code{std::map}.

The validation the \code{std::list} and \code{std::deque} tests is 
performed using the \code{validate} methods explained in Section 
\ref{sec-common-validation-methods}.

The code for these tests may be found in Appendix 
\ref{sec-code-test-read-cont}.

\subsubsection{Results}
The following is the output from the test programme; it indicates 
that the GDFA Library passes these tests.

\begin{flushleft} \small \label{part83}
\colorbox{light}{$\langle$output of testreadcont.cpp {\footnotesize \hypertarget{94}{94}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@Test:   testreadcont.cpp@\\
\mbox{}\verb@@\\
\mbox{}\verb@Test Reading from Standard Library Containers@\\
\mbox{}\verb@*********************************************@\\
\mbox{}\verb@@\\
\mbox{}\verb@Results:@\\
\mbox{}\verb@@\\
\mbox{}\verb@Results for reading from a vector, used for comparison testing@\\
\mbox{}\verb@Number of words beginning with each letter, case insensitive@\\
\mbox{}\verb@a: 3228@\\
\mbox{}\verb@b: 1417@\\
\mbox{}\verb@c: 1255@\\
\mbox{}\verb@d: 894@\\
\mbox{}\verb@e: 532@\\
\mbox{}\verb@f: 1020@\\
\mbox{}\verb@g: 661@\\
\mbox{}\verb@h: 2394@\\
\mbox{}\verb@i: 2020@\\
\mbox{}\verb@j: 94@\\
\mbox{}\verb@k: 200@\\
\mbox{}\verb@l: 740@\\
\mbox{}\verb@m: 1080@\\
\mbox{}\verb@n: 639@\\
\mbox{}\verb@o: 1653@\\
\mbox{}\verb@p: 813@\\
\mbox{}\verb@q: 64@\\
\mbox{}\verb@r: 544@\\
\mbox{}\verb@s: 2365@\\
\mbox{}\verb@t: 4282@\\
\mbox{}\verb@u: 396@\\
\mbox{}\verb@v: 163@\\
\mbox{}\verb@w: 2108@\\
\mbox{}\verb@x: 1@\\
\mbox{}\verb@y: 460@\\
\mbox{}\verb@z: 2@\\
\mbox{}\verb@default: 823@\\
\mbox{}\verb@@\\
\mbox{}\verb@Testing reading from a deque@\\
\mbox{}\verb@Passed test for reading from a deque@\\
\mbox{}\verb@Testing reading from a list@\\
\mbox{}\verb@Passed test for reading from a list@\\
\mbox{}\verb@Testing reading from a multiset@\\
\mbox{}\verb@Passed test for reading from a multiset@\\
\mbox{}\verb@Testing reading from a map@\\
\mbox{}\verb@Passed test for reading from a map@\\
\mbox{}\verb@@\\
\mbox{}\verb@*************     END OF RESULTS     *************@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Not used.
\end{list}
\end{flushleft}
\subsection{Test Array as Input}
\subsubsection{Test Objective}
This set of tests is intended to validate that the GDFA work properly 
with an array as the input container and a pointer as the input 
iterator.

\subsubsection{Description}
This test uses the \code{word\_sorter} derived \code{destination} 
class to sort \code{std::strings} in the input range based on their 
first characters (insensitive to case). 

This test validates the use of array as the container to hold the 
input range. Two pointers, which are valid \code{InputIterator}s, are 
used to specify the beginning and end of the data range contained in 
the array.

When using an array as input, the address of the first element must 
be passed as the iterator pointing to the first element of the input 
range and the address of one past the last element must be passed to 
point to one past the last element in the input range. This is 
accomplished by indexing the first element of the array and the 
memory location one past the last element in the array and passing 
these memory locations by reference to the \code{router.distribute()} 
member function.

The test is administered as follows: First, we read the input into a 
\code{std::vector$<$std::string$>$} for storage. Second, we copy the 
input to an array for testing. Third, we distribute the data from 
both the array and the vector using the constructed router object. 
Forth, we validate the results of the array based distribution by 
comparing them to the results of the vector based distribution.

The array validation is performed using the \code{validate} methods 
explained in Section \ref{sec-common-validation-methods}.

The code for this test may be found in \ref{sec-code-test-array}.

\subsubsection{Results}
The following is the output from the test programme; it indicates 
that the GDFA Library passes these tests.

\begin{flushleft} \small \label{part84}
\colorbox{light}{$\langle$output from testarray.cpp {\footnotesize \hypertarget{96}{96}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@Test:  testarray.cpp@\\
\mbox{}\verb@@\\
\mbox{}\verb@Test Using an Array as input.@\\
\mbox{}\verb@***********************************@\\
\mbox{}\verb@@\\
\mbox{}\verb@Results:@\\
\mbox{}\verb@@\\
\mbox{}\verb@a: 3228@\\
\mbox{}\verb@b: 1417@\\
\mbox{}\verb@c: 1255@\\
\mbox{}\verb@d: 894@\\
\mbox{}\verb@e: 532@\\
\mbox{}\verb@f: 1020@\\
\mbox{}\verb@g: 661@\\
\mbox{}\verb@h: 2394@\\
\mbox{}\verb@i: 2020@\\
\mbox{}\verb@j: 94@\\
\mbox{}\verb@k: 200@\\
\mbox{}\verb@l: 740@\\
\mbox{}\verb@m: 1080@\\
\mbox{}\verb@n: 639@\\
\mbox{}\verb@o: 1653@\\
\mbox{}\verb@p: 813@\\
\mbox{}\verb@q: 64@\\
\mbox{}\verb@r: 544@\\
\mbox{}\verb@s: 2365@\\
\mbox{}\verb@t: 4282@\\
\mbox{}\verb@u: 396@\\
\mbox{}\verb@v: 163@\\
\mbox{}\verb@w: 2108@\\
\mbox{}\verb@x: 1@\\
\mbox{}\verb@y: 460@\\
\mbox{}\verb@z: 2@\\
\mbox{}\verb@default: 823@\\
\mbox{}\verb@@\\
\mbox{}\verb@Testing using an array as input@\\
\mbox{}\verb@Passed array input test@\\
\mbox{}\verb@@\\
\mbox{}\verb@*************     END OF RESULTS     *************@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Not used.
\end{list}
\end{flushleft}
\subsection{Tests Reading from and Writing to Files}
\subsubsection{Test Objective}
This set of tests validates that the GDFA is able to work properly 
while reading and writing to files via \code{std::iostream}s in the 
\code{destination} objects.

\subsubsection{Description}
This test validates the use of \code{std::iostream}s in the 
\code{destination} objects. This test complements a previous test in 
that it also writes directly to files.

In the test we use an \code{std::ifstream} to initialise the 
\code{InputIterator} given to \code{router.distribute()} and an 
\code{std::ofstream} to initialise the \code{OutputIterator} used in 
the \code{destination} classes. The functionality is the same as in 
the previous examples using word sorter except for the source and 
destination of the data.  The results of the test are stored in files 
labeled "output\_alpha" where ``alpha'' takes a value $[a-z]$ or 
"default".

The element type in this test is \code{std::string}.

The validation test is by necessity a seperate programme from the 
actual test, because the test outputs the results to files, rather 
than a storage container that can be easily checked. The code for 
this test may be found in Appendix \ref{sec-code-test-file-io}.

Thus the validation test works as follows: it reads each file 
generated by the test, and checks to make sure that the letter that 
starts each string in the file is the appropriate letter for that 
file.  The default case is validated by making sure that no character 
in the ranges $[A-Z]$ or $[a-z]$ start a string in the default case 
file.

\subsubsection{Results}
The following is the output from the test programme; it indicates 
that the GDFA Library passes these tests.

\begin{flushleft} \small \label{part85}
\colorbox{light}{$\langle$output from testrwfiles.cpp {\footnotesize \hypertarget{97}{97}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@output from testrwfiles.cpp@\\
\mbox{}\verb@@\\
\mbox{}\verb@Test:  testrwfiles.cpp@\\
\mbox{}\verb@@\\
\mbox{}\verb@Test of reading and writing from and to files with ifstream and ofstream.@\\
\mbox{}\verb@*********************************************************@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@*************     END OF TEST     *************@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@Test:  validaterwfiles.cpp@\\
\mbox{}\verb@@\\
\mbox{}\verb@Validating the testrwfiles test. @\\
\mbox{}\verb@*********************************************************@\\
\mbox{}\verb@@\\
\mbox{}\verb@Results:@\\
\mbox{}\verb@@\\
\mbox{}\verb@Passed rwfiles test@\\
\mbox{}\verb@@\\
\mbox{}\verb@*************     END OF RESULTS     *************@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Not used.
\end{list}
\end{flushleft}
\subsection{Testing \code{std::istream\_iterator}s with Built-In Types}
\subsubsection{Test Set Objective}
The purpose of this set of tests is to validate that GDFA works 
properly if an \code{std::istream\_iterator<element\_type>} is used 
to define the input range operated on by the 
\code{router.distribute()} member function. Essentially, it tests 
that GDFA works using file streams via input file stream iterators 
using $4$ element types (\code{char}, \code{std::string}, \code{int}, 
\code{double}).

\subsubsection{Description}
This set of tests reads from standard input, distributes the data and 
finally performs a validation test. There are $4$ tests in this set: 
\code{int}, \code{double}, \code{char}, \code{std::string}.

Following are descriptions for each of the $4$ tests.

\paragraph{Testing \code{std::istream\_iterator<int>}}
This test ensures that using an \code{std::istream\_iterator} type as 
the input to \code{router.distribute()} will result in the correct 
operation of the GDFA library.

This test takes as input a series of \code{int}s in the range 
$[0,1000000]$ from standard input. The \code{router} class will then 
sort the input into $10$ ranges:

\begin{itemize}
\item $(0,100000)$ \item $(100000,200000)$ \item $(200000,300000)$ 
\item $(300000,400000)$ \item $(400000,500000)$ \item 
$(500000,600000)$ \item $(600000,700000)$ \item $(700000,800000)$ 
\item $(800000,900000)$ \item $(900000,1000000)$
\end{itemize}

A default case handles all other values.

A validation test is performed that checks the maximum and minimum 
element in each filtered container to ensure that all elements in the 
container are correctly distributed.

To generate input, a sample programme is included (generateints.cpp; 
see Appendix \ref{sec-code-test-gen-ints}) that takes as a 
command-line argument the number of integers to generate and prints 
to the command-line that many integers in the range $[0,1000000)$.

The code for this test may be found in Appendix 
\ref{sec-code-test-istream-int}.

\paragraph{Testing \code{std::istream\_iterator<double>}}
This test is to ensure that using an 
\code{std::istream\_iterator<double>} will result in the correct 
operation of the GDFA library.

This test takes as input a series of \code{double}s in the range 
$[0,1]$ from standard input. The \code{router} class will then sort 
the input into $10$ ranges:

\begin{itemize}
\item $(0.0,0.1)$ \item $(0.1,0.2)$ \item $(0.2,0.3)$ \item 
$(0.3,0.4)$ \item $(0.4,0.5)$ \item $(0.5,0.6)$ \item $(0.6,0.7)$ 
\item $(0.7,0.8)$ \item $(0.8,0.9)$ \item $(0.9,1.0)$
\end{itemize}

A default case handles all other values.

A validation test is performed that checks the maximum and minimum 
element in each filtered container to ensure that all elements in the 
container are correctly filtered.

To generate input, a sample programme is included 
(generatedoubles.cpp; see Appendix \ref{sec-code-test-gen-doubles}) 
that takes as a command-line argument the number of integers to 
generate and prints to the command-line that many doubles in the 
range $[0,1]$.

The code for this test may be found in Appendix 
\ref{sec-code-test-istream-double}.

\paragraph{Testing \code{std::istream\_iterator<char>}}
This test is to ensure that using an 
\code{std::istream\_iterator<char>} will result in the correct 
operation of the GDFA library.

This test takes as input text from standard input and attempts to 
sort the input according to the value of each character that is read. 
The input is filtered into $27$ containers, one for each letter of 
the alphabet (uppercase and lowercase are treated as being the same) 
and a default case to catch all other characters. Note that the 
default configuration for an \code{std::istream\_iterator} is to 
ignore whitespace (space, tab and new line characters) meaning that 
the number of characters output by the test may not be the same as 
the number of characters in the input.

The test outputs the number of characters of each type that it sees. 
For a validation test it checks each container to ensure that only 
the correct letter is in the appropriate container. For the default 
case the validation test is to make sure that there are no letters in 
the default container, where a letter is $[A-Z]$ or $[a-z]$.

The code for this test may be found in Appendix 
\ref{sec-code-test-istream-char}.

\paragraph{Testing \code{std::istream\_iterator<std::string>}}
This test is to ensure that using an 
\code{std::istream\_iterator<std::string>} will result in the correct 
operation of the GDFA library.

This test takes as input text from standard input and attempts to 
sort the input according to the value of the first letter of the 
string that is read. The input is filtered into $27$ containers, one 
for each letter of the alphabet (uppercase and lowercase are treated 
as being the same) and a default case to catch all other characters.

The test outputs the number of strings that begin with each letter 
that it sees. For a validation test it checks each container to 
ensure that only strings beginning with the appropriate letter are in 
the appropriate container. For the default case the validation test 
is to make sure that there are no \code{std::strings} beginning with 
a letter in the default container, where a letter is $[A-Z]$ or 
$[a-z]$.

The code for this test may be found in Appendix 
\ref{sec-code-test-istream-string}.

\subsubsection{Results}
The following results all confirm that the GDFA Library functions 
properly when used with \code{std::istream\_iterator}s.

\paragraph{Test with \code{std::istream\_iterator<char>}}
\begin{flushleft} \small \label{part86}
\colorbox{light}{$\langle$output from test\_char\_istream.cpp {\footnotesize \hypertarget{100}{100}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@Test:  test_char_istream.cpp@\\
\mbox{}\verb@@\\
\mbox{}\verb@Test Uses istream iterator and type char as input.@\\
\mbox{}\verb@***********************************@\\
\mbox{}\verb@@\\
\mbox{}\verb@Results:@\\
\mbox{}\verb@@\\
\mbox{}\verb@a: 9695@\\
\mbox{}\verb@b: 2055@\\
\mbox{}\verb@c: 3308@\\
\mbox{}\verb@d: 5903@\\
\mbox{}\verb@e: 15657@\\
\mbox{}\verb@f: 2574@\\
\mbox{}\verb@g: 3096@\\
\mbox{}\verb@h: 8543@\\
\mbox{}\verb@i: 8797@\\
\mbox{}\verb@j: 144@\\
\mbox{}\verb@k: 1052@\\
\mbox{}\verb@l: 4796@\\
\mbox{}\verb@m: 3020@\\
\mbox{}\verb@n: 8340@\\
\mbox{}\verb@o: 10218@\\
\mbox{}\verb@p: 2294@\\
\mbox{}\verb@q: 103@\\
\mbox{}\verb@r: 7522@\\
\mbox{}\verb@s: 8233@\\
\mbox{}\verb@t: 11564@\\
\mbox{}\verb@u: 3568@\\
\mbox{}\verb@v: 1086@\\
\mbox{}\verb@w: 3157@\\
\mbox{}\verb@x: 199@\\
\mbox{}\verb@y: 2486@\\
\mbox{}\verb@z: 85@\\
\mbox{}\verb@Number of elements caught by default case: 7903@\\
\mbox{}\verb@Passed Validation Test@\\
\mbox{}\verb@@\\
\mbox{}\verb@*************     END OF RESULTS     *************@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Not used.
\end{list}
\end{flushleft}
\paragraph{Test with \code{std::istream\_iterator<std::string>}}
\begin{flushleft} \small \label{part87}
\colorbox{light}{$\langle$output from test\_string\_istream.cpp {\footnotesize \hypertarget{101}{101}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@Test:  test_string_istream.cpp@\\
\mbox{}\verb@@\\
\mbox{}\verb@Test Uses istream iterator and type string as input.@\\
\mbox{}\verb@***********************************@\\
\mbox{}\verb@@\\
\mbox{}\verb@Results:@\\
\mbox{}\verb@@\\
\mbox{}\verb@a: 3228@\\
\mbox{}\verb@b: 1417@\\
\mbox{}\verb@c: 1255@\\
\mbox{}\verb@d: 894@\\
\mbox{}\verb@e: 532@\\
\mbox{}\verb@f: 1020@\\
\mbox{}\verb@g: 661@\\
\mbox{}\verb@h: 2394@\\
\mbox{}\verb@i: 2020@\\
\mbox{}\verb@j: 94@\\
\mbox{}\verb@k: 200@\\
\mbox{}\verb@l: 740@\\
\mbox{}\verb@m: 1080@\\
\mbox{}\verb@n: 639@\\
\mbox{}\verb@o: 1653@\\
\mbox{}\verb@p: 813@\\
\mbox{}\verb@q: 64@\\
\mbox{}\verb@r: 544@\\
\mbox{}\verb@s: 2365@\\
\mbox{}\verb@t: 4282@\\
\mbox{}\verb@u: 396@\\
\mbox{}\verb@v: 163@\\
\mbox{}\verb@w: 2108@\\
\mbox{}\verb@x: 1@\\
\mbox{}\verb@y: 460@\\
\mbox{}\verb@z: 2@\\
\mbox{}\verb@Number of elements caught by default case: 823@\\
\mbox{}\verb@Passed Validation Test@\\
\mbox{}\verb@@\\
\mbox{}\verb@*************     END OF RESULTS     *************@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Not used.
\end{list}
\end{flushleft}
\paragraph{Test with \code{std::istream\_iterator<int>}}
\begin{flushleft} \small \label{part88}
\colorbox{light}{$\langle$output from test\_int\_istream.cpp {\footnotesize \hypertarget{102a}{102a}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@Test:  test_int_istream.cpp@\\
\mbox{}\verb@@\\
\mbox{}\verb@Test Uses istream iterator and type int as input.@\\
\mbox{}\verb@***********************************@\\
\mbox{}\verb@@\\
\mbox{}\verb@Results:@\\
\mbox{}\verb@@\\
\mbox{}\verb@number of elements in each range, with the max and min element in the ranges@\\
\mbox{}\verb@(0,100000): 9853 99993 13@\\
\mbox{}\verb@(100000,200000): 10013 199985 100022@\\
\mbox{}\verb@(200000,300000): 10087 299968 200013@\\
\mbox{}\verb@(300000,400000): 10145 399999 300004@\\
\mbox{}\verb@(400000,500000): 9944 499960 400006@\\
\mbox{}\verb@(500000,600000): 9984 599989 500034@\\
\mbox{}\verb@(600000,700000): 10025 699993 600023@\\
\mbox{}\verb@(700000,800000): 9863 799997 700001@\\
\mbox{}\verb@(800000,900000): 10040 899997 800013@\\
\mbox{}\verb@(900000,1000000): 10045 999964 900008@\\
\mbox{}\verb@Number elements caught by default case: 1@\\
\mbox{}\verb@Passed Validation Test@\\
\mbox{}\verb@@\\
\mbox{}\verb@*************     END OF RESULTS     *************@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Not used.
\end{list}
\end{flushleft}
\paragraph{Test with \code{std::istream\_iterator<double>}}
\begin{flushleft} \small \label{part89}
\colorbox{light}{$\langle$output from test\_double\_istream.cpp {\footnotesize \hypertarget{102b}{102b}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@Test:  test_double_istream.cpp@\\
\mbox{}\verb@@\\
\mbox{}\verb@Test Uses istream iterator and type double as input.@\\
\mbox{}\verb@***********************************@\\
\mbox{}\verb@@\\
\mbox{}\verb@Results:@\\
\mbox{}\verb@@\\
\mbox{}\verb@number of elements in each range, with the max and min element in the ranges@\\
\mbox{}\verb@(0,0.1): 10084 0.0999923 2.3006e-06@\\
\mbox{}\verb@(0.1,0.2): 9967 0.199997 0.100015@\\
\mbox{}\verb@(0.2,0.3): 9898 0.299995 0.200009@\\
\mbox{}\verb@(0.3,0.4): 10059 0.399989 0.30001@\\
\mbox{}\verb@(0.4,0.5): 10120 0.499999 0.400008@\\
\mbox{}\verb@(0.5,0.6): 9930 0.599995 0.500007@\\
\mbox{}\verb@(0.6,0.7): 10002 0.699988 0.600007@\\
\mbox{}\verb@(0.7,0.8): 10039 0.799995 0.700002@\\
\mbox{}\verb@(0.8,0.9): 9863 0.899999 0.800033@\\
\mbox{}\verb@(0.9,1): 10037 0.999996 0.900004@\\
\mbox{}\verb@Number of elements caught by default case: 1@\\
\mbox{}\verb@Passed Validation Test@\\
\mbox{}\verb@@\\
\mbox{}\verb@*************     END OF RESULTS     *************@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Not used.
\end{list}
\end{flushleft}
\subsection{Testing Unexpected Conditions}
This section explores several boundary conditions for the 
\code{router} class.

First, we run the GDFA without adding any \code{destination}s to the 
\code{router} object. The proper functionality would be for the GDFA 
to nothing.

The code for this test may be found in Appendix 
\ref{sec-code-test-no-destinations}.

Second, we run the GDFA with an input range that is empty. The proper 
action is to do nothing, which results in unaltered containers (the 
call to \code{router.distribute()} results in nothing being written 
to the locations pointed to by its \code{destination} objects' 
\code{OutputIterator}s.

The code for this test may be found in Appendix 
\ref{sec-code-test-no-input}.

\subsubsection{Test Objective}
This set of tests attempts to determine how the GDFA would behave 
under certain atypical conditions. These are conditions which are 
incongruous with the logical operation of the library. However, it is 
desirable for the \code{router} class to be robust and as such 
operate satisfactorily and predictably under these conditions.

\subsubsection{Results}
These results indicate that the \code{router} class is able to 
properly handle the boundary conditions specified.

\paragraph{Test of \code{router} with no \code{destination}s}
\begin{flushleft} \small \label{part90}
\colorbox{light}{$\langle$output of nodestinations.cpp {\footnotesize \hypertarget{104a}{104a}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@Test:  nodestinations.cpp@\\
\mbox{}\verb@@\\
\mbox{}\verb@Test router without adding and destinations to it.@\\
\mbox{}\verb@**************************************************@\\
\mbox{}\verb@@\\
\mbox{}\verb@Results:@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@*************     END OF RESULTS     *************@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Not used.
\end{list}
\end{flushleft}
\paragraph{Test of \code{router} with no Input}
\begin{flushleft} \small \label{part91}
\colorbox{light}{$\langle$output of noinput.cpp {\footnotesize \hypertarget{104b}{104b}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@Test:  noinput.cpp@\\
\mbox{}\verb@@\\
\mbox{}\verb@Test behavior of router on an empty input range.@\\
\mbox{}\verb@********************************************@\\
\mbox{}\verb@@\\
\mbox{}\verb@Results:@\\
\mbox{}\verb@@\\
\mbox{}\verb@a: 0@\\
\mbox{}\verb@b: 0@\\
\mbox{}\verb@c: 0@\\
\mbox{}\verb@d: 0@\\
\mbox{}\verb@e: 0@\\
\mbox{}\verb@f: 0@\\
\mbox{}\verb@g: 0@\\
\mbox{}\verb@h: 0@\\
\mbox{}\verb@i: 0@\\
\mbox{}\verb@j: 0@\\
\mbox{}\verb@k: 0@\\
\mbox{}\verb@l: 0@\\
\mbox{}\verb@m: 0@\\
\mbox{}\verb@n: 0@\\
\mbox{}\verb@o: 0@\\
\mbox{}\verb@p: 0@\\
\mbox{}\verb@q: 0@\\
\mbox{}\verb@r: 0@\\
\mbox{}\verb@s: 0@\\
\mbox{}\verb@t: 0@\\
\mbox{}\verb@u: 0@\\
\mbox{}\verb@v: 0@\\
\mbox{}\verb@w: 0@\\
\mbox{}\verb@x: 0@\\
\mbox{}\verb@y: 0@\\
\mbox{}\verb@z: 0@\\
\mbox{}\verb@Default: 0@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@*************     END OF RESULTS     *************@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Not used.
\end{list}
\end{flushleft}
\chapter{Conclusion}
\section{Summary}
This report presents the GDFA Library. The goal in so doing is to 
demonstrate and explain the usefulness of the GDFA Library through a 
broad conceptual overview and a practical set of ``learn by example'' 
applications. Technical information and complete set of descriptions 
of the GDFA Library components and features is also provided.

The testing of the GDFA Library components demonstrates their 
correctness and efficiency. The correctness tests demonstrate that 
the components work properly with an exhaustive set of relevant 
Standard Library types and built-in types. Additionally, a variety of 
priority configurations as well as unexpected situations are tested. 
The components perform correctly and predictably in all tests.

The efficiency tests include timed tests and operation counting 
tests. These methods are used in order to establish a sound 
foundation for our conclusions. Both tests clearly show that the 
algorithms used in the GDFA Library are linear with respect to $N$ 
(the input range size) and $M$ (the number of \code{destination}s) 
and is consequently an \code{O(MN)} algorithm. These results are 
exactly what we expect. In practice, the GDFA Library is likely to be 
used with a large input size ($N$) and a modest number of 
destinations ($M$). Consequently, the linear running time with 
respect to $N$ is of primary importance to users of the library.

\section{Future of the GDFA Library}
While the foundation of the GDFA Library is the simple 
\code{distribute} function, it has already been extended into the 
more powerful set of components presented in this document. These 
components make use of sub-type polymorphism (inheritance and virtual 
functions), the functor concept, iterators, and extensive parametric 
polymorphism (C++ templates).\footnote{The capabilities used to 
create this feature set gracefully permute into countless empowering 
abstractions. The result is a supple and powerful set of components 
with virtually unlimited applications.}

Many future opportunities exist for the library: in terms of network 
programming, generalised multi-level distribution, and thread safety.

It is clear from the examples presented in the tutorial and testing 
sections that the GDFA components would work well with a networked 
application. Therefore, a fully implemented example of this sort 
would be a nice extension of this project and would complement our 
existing examples.

Another interesting application is an integrated multi-level 
distribution and filtering paradigm. This concept is used in the 
criminal profiling example in the tutorial. A larger application of 
these notions would be a very interesting extension of this project.

Finally, a thread-safe version of GDFA, in the sense that it would 
allow the user to add and delete \code{destination} objects while the 
application is running, would allow the combination of the above two 
ideas in a single comprehensive application. Specifically, this 
ability would facilitate the creation of a multi-level filtering 
paradigm running in tandem on multiple processors in multiple 
locations, each running a particular layer of the filter. The 
application would be continually running; as such the ability to 
maintain (update) the filtering configuration would be necessary. 
Currently, this setup is possible if the \code{destination} 
configurations are not changed. However, this could be made easier if 
the startup of the algorithm were constructed to be more flexible. 
Basically, the \code{router} objects must be willing to wait for a 
subsequent iteration on their input streams rather than terminate. 
Without belaboring additional implementation issues, it is fair to 
say that this would constitute a substantial increase in 
functionality.

\section{Final Thoughts}
We hope that the GDFA Library will be a powerful new set of 
components with many useful applications over a wide range of 
software development and programming problems. We strongly encourage 
the reader to use, extend, and modify the GDFA Library to tackle new 
problems in distribution and filtering.

\appendix
\chapter{Code for Timed Tests}
\section{Test 1}
\subsection{Test 1a}
\label{sec-code-test1a}

\begin{flushleft} \small \label{part92}
\verb@"timed_test1a.cpp"@ {\footnotesize \hypertarget{108}{108} }$\equiv$
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@#include <cmath>@\\
\mbox{}\verb@#include <cstdlib>@\\
\mbox{}\verb@#include <ctime>@\\
\mbox{}\verb@#include <iostream>@\\
\mbox{}\verb@#include <vector>@\\
\mbox{}\verb@#include <algorithm>@\\
\mbox{}\verb@#include "timer.h"@\\
\mbox{}\verb@#include <iostream>@\\
\mbox{}\verb@#include <vector>@\\
\mbox{}\verb@#include <list>@\\
\mbox{}\verb@#include <iterator>@\\
\mbox{}\verb@@\\
\mbox{}\verb@#include "router.hpp"@\\
\mbox{}\verb@@\\
\mbox{}\verb@using namespace std;@\\
\mbox{}\verb@using std::cout;@\\
\mbox{}\verb@using std::endl;@\\
\mbox{}\verb@using std::vector;@\\
\mbox{}\verb@using std::list;@\\
\mbox{}\verb@using std::back_inserter;@\\
\mbox{}\verb@using std::ostream_iterator;@\\
\mbox{}\verb@using std::back_insert_iterator;@\\
\mbox{}\verb@@\\
\mbox{}\verb@using gdfa::router;@\\
\mbox{}\verb@using gdfa::destination;@\\
\mbox{}\verb@@\\
\mbox{}\verb@template <typename OutputIterator>@\\
\mbox{}\verb@class less_than_n : public destination<int>@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  private:@\\
\mbox{}\verb@    OutputIterator out;@\\
\mbox{}\verb@    int n;@\\
\mbox{}\verb@    @\\
\mbox{}\verb@  public:@\\
\mbox{}\verb@    less_than_n(OutputIterator _out, int _n) : out(_out), n(_n) {}@\\
\mbox{}\verb@    @\\
\mbox{}\verb@    bool distribute(const int& element)@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      if (element < n)@\\
\mbox{}\verb@      {@\\
\mbox{}\verb@        *(out++) = element;@\\
\mbox{}\verb@        return false;//continue filtering@\\
\mbox{}\verb@      }@\\
\mbox{}\verb@      @\\
\mbox{}\verb@      return false;    @\\
\mbox{}\verb@    }@\\
\mbox{}\verb@};@\\
\mbox{}\verb@@\\
\mbox{}\verb@template <typename OutputIterator>@\\
\mbox{}\verb@class my_default : public destination<int>@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  private:@\\
\mbox{}\verb@    OutputIterator out;@\\
\mbox{}\verb@    @\\
\mbox{}\verb@  public:@\\
\mbox{}\verb@    my_default(OutputIterator _out) : out(_out) {}@\\
\mbox{}\verb@    @\\
\mbox{}\verb@    bool distribute(const int& n)@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      *(out++) = n;@\\
\mbox{}\verb@      return true;@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@};@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@void test() {@\\
\mbox{}\verb@  cout << "Test 1a\nTesting N\nTiming distribute on integers.\n";@\\
\mbox{}\verb@  cout << "Distribute to all destinations." << endl;@\\
\mbox{}\verb@ srand(time(0));@\\
\mbox{}\verb@@\\
\mbox{}\verb@  // Initial Setup@\\
\mbox{}\verb@  router<int> *r;@\\
\mbox{}\verb@  r = new router<int>;@\\
\mbox{}\verb@  vector<int> v, out1, out2, out3, defaultItems;@\\
\mbox{}\verb@  vector<int> out1_saved, out2_saved, defaultItems_saved;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  typedef std::back_insert_iterator<std::vector<int> > BItype;@\\
\mbox{}\verb@    delete r;@\\
\mbox{}\verb@    r = new router<int>;@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  out1.clear();@\\
\mbox{}\verb@  out2.clear();@\\
\mbox{}\verb@  out3.clear();@\\
\mbox{}\verb@  defaultItems.clear();@\\
\mbox{}\verb@@\\
\mbox{}\verb@  less_than_n<BItype> test1(back_inserter(out1), 1048576);@\\
\mbox{}\verb@  less_than_n<BItype> test2(back_inserter(out2), 1048576);@\\
\mbox{}\verb@  less_than_n<BItype> test3(back_inserter(out3), 1048576);@\\
\mbox{}\verb@  my_default<BItype> defaultTest(back_inserter(defaultItems)); @\\
\mbox{}\verb@  @\\
\mbox{}\verb@  r->add_destination(test1);@\\
\mbox{}\verb@  r->add_destination(test2);@\\
\mbox{}\verb@  r->add_destination(test3);@\\
\mbox{}\verb@  r->set_default(defaultTest);@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@  unsigned long N, N1, N2;@\\
\mbox{}\verb@  unsigned int reps;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  N1 = 1;@\\
\mbox{}\verb@  N2 = 1048576;@\\
\mbox{}\verb@  reps = 10;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  timer tim;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  for (N = N1; N <= N2; N *= 2) {@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@      v.clear(); @\\
\mbox{}\verb@    v.reserve(N);@\\
\mbox{}\verb@    for (int i = 0; i < N; ++i) {@\\
\mbox{}\verb@    v.push_back(i);@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@@\\
\mbox{}\verb@    // Compute the baseline time for N@\\
\mbox{}\verb@    tim.start_baseline(reps);@\\
\mbox{}\verb@    do { @\\
\mbox{}\verb@    //////////////////////////////  @\\
\mbox{}\verb@      // Baseline Operations Here @\\
\mbox{}\verb@@\\
\mbox{}\verb@  out1.clear();@\\
\mbox{}\verb@  out2.clear();  @\\
\mbox{}\verb@  out3.clear();@\\
\mbox{}\verb@  defaultItems.clear();@\\
\mbox{}\verb@@\\
\mbox{}\verb@    // End of Baseline Operations@\\
\mbox{}\verb@    ///////////////////////////////@\\
\mbox{}\verb@    } while (tim.check());@\\
\mbox{}\verb@    tim.report(false);@\\
\mbox{}\verb@@\\
\mbox{}\verb@    tim.start(reps, N);@\\
\mbox{}\verb@    do {@\\
\mbox{}\verb@@\\
\mbox{}\verb@    //////////////////////////////  @\\
\mbox{}\verb@      // Baseline Operations Here @\\
\mbox{}\verb@  @\\
\mbox{}\verb@  out1.clear();@\\
\mbox{}\verb@  out2.clear();@\\
\mbox{}\verb@     out3.clear();@\\
\mbox{}\verb@  defaultItems.clear();@\\
\mbox{}\verb@  @\\
\mbox{}\verb@    // End of Baseline Operations@\\
\mbox{}\verb@    ///////////////////////////////@\\
\mbox{}\verb@    // Main Timed Operation@\\
\mbox{}\verb@  r->distribute(v.begin(), v.end());@\\
\mbox{}\verb@    //////////////////////////////////////@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@    while (tim.check());@\\
\mbox{}\verb@    tim.report(false);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@\\
\mbox{}\verb@int main()@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  test();  @\\
\mbox{}\verb@  return 0;@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@
\end{list}
\vspace{-2ex}
\end{flushleft}
\subsection{Test 1b}
\label{sec-code-test1b}

\begin{flushleft} \small \label{part93}
\verb@"timed_test1b.cpp"@ {\footnotesize \hypertarget{111}{111} }$\equiv$
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@#include <cmath>@\\
\mbox{}\verb@#include <cstdlib>@\\
\mbox{}\verb@#include <ctime>@\\
\mbox{}\verb@#include <iostream>@\\
\mbox{}\verb@#include <vector>@\\
\mbox{}\verb@#include <algorithm>@\\
\mbox{}\verb@#include "timer.h"@\\
\mbox{}\verb@#include <iostream>@\\
\mbox{}\verb@#include <vector>@\\
\mbox{}\verb@#include <list>@\\
\mbox{}\verb@#include <iterator>@\\
\mbox{}\verb@@\\
\mbox{}\verb@#include "router.hpp"@\\
\mbox{}\verb@@\\
\mbox{}\verb@using namespace std;@\\
\mbox{}\verb@using std::cout;@\\
\mbox{}\verb@using std::endl;@\\
\mbox{}\verb@using std::vector;@\\
\mbox{}\verb@using std::list;@\\
\mbox{}\verb@using std::back_inserter;@\\
\mbox{}\verb@using std::ostream_iterator;@\\
\mbox{}\verb@using std::back_insert_iterator;@\\
\mbox{}\verb@@\\
\mbox{}\verb@using gdfa::router;@\\
\mbox{}\verb@using gdfa::destination;@\\
\mbox{}\verb@@\\
\mbox{}\verb@template <typename OutputIterator>@\\
\mbox{}\verb@class less_than_n : public destination<int>@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  private:@\\
\mbox{}\verb@    OutputIterator out;@\\
\mbox{}\verb@    int n;@\\
\mbox{}\verb@    @\\
\mbox{}\verb@  public:@\\
\mbox{}\verb@    less_than_n(OutputIterator _out, int _n) : out(_out), n(_n) {}@\\
\mbox{}\verb@    @\\
\mbox{}\verb@    bool distribute(const int& element)@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      if (element > n)@\\
\mbox{}\verb@      {@\\
\mbox{}\verb@        *(out++) = element;@\\
\mbox{}\verb@        return false;//continue filtering@\\
\mbox{}\verb@      }@\\
\mbox{}\verb@      @\\
\mbox{}\verb@      return false;    @\\
\mbox{}\verb@    }@\\
\mbox{}\verb@};@\\
\mbox{}\verb@@\\
\mbox{}\verb@template <typename OutputIterator>@\\
\mbox{}\verb@class my_default : public destination<int>@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  private:@\\
\mbox{}\verb@    OutputIterator out;@\\
\mbox{}\verb@    @\\
\mbox{}\verb@  public:@\\
\mbox{}\verb@    my_default(OutputIterator _out) : out(_out) {}@\\
\mbox{}\verb@    @\\
\mbox{}\verb@    bool distribute(const int& n)@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      *(out++) = n;@\\
\mbox{}\verb@      return true;@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@};@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@void test() {@\\
\mbox{}\verb@  cout << "Test 1b\nTesting N\nTiming distribute on integers.\n";@\\
\mbox{}\verb@  cout << "Distribute to just 1 of the destinations." << endl;@\\
\mbox{}\verb@  srand(time(0));@\\
\mbox{}\verb@@\\
\mbox{}\verb@  // Initial Setup@\\
\mbox{}\verb@  router<int> *r;@\\
\mbox{}\verb@  r = new router<int>;@\\
\mbox{}\verb@  vector<int> v, out1, out2, out3, defaultItems;@\\
\mbox{}\verb@  vector<int> out1_saved, out2_saved, defaultItems_saved;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  typedef std::back_insert_iterator<std::vector<int> > BItype;@\\
\mbox{}\verb@    delete r;@\\
\mbox{}\verb@    r = new router<int>;@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  out1.clear();@\\
\mbox{}\verb@  out2.clear();@\\
\mbox{}\verb@  out3.clear();@\\
\mbox{}\verb@  defaultItems.clear();@\\
\mbox{}\verb@@\\
\mbox{}\verb@  less_than_n<BItype> test1(back_inserter(out1), 1048576);@\\
\mbox{}\verb@  less_than_n<BItype> test2(back_inserter(out2), 1048576);@\\
\mbox{}\verb@  less_than_n<BItype> test3(back_inserter(out3), 1048576);@\\
\mbox{}\verb@  my_default<BItype> defaultTest(back_inserter(defaultItems)); @\\
\mbox{}\verb@  @\\
\mbox{}\verb@  r->add_destination(test1);@\\
\mbox{}\verb@  r->add_destination(test2);@\\
\mbox{}\verb@  r->add_destination(test3);@\\
\mbox{}\verb@  r->set_default(defaultTest);@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@  unsigned long N, N1, N2;@\\
\mbox{}\verb@  unsigned int reps;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  N1 = 1;@\\
\mbox{}\verb@  N2 = 1048576;@\\
\mbox{}\verb@  reps = 10;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  timer tim;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  for (N = N1; N <= N2; N *= 2) {@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@      v.clear(); @\\
\mbox{}\verb@    v.reserve(N);@\\
\mbox{}\verb@    for (int i = 0; i < N; ++i) {@\\
\mbox{}\verb@    v.push_back(i);@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@@\\
\mbox{}\verb@    // Compute the baseline time for N@\\
\mbox{}\verb@    tim.start_baseline(reps);@\\
\mbox{}\verb@    do { @\\
\mbox{}\verb@    //////////////////////////////  @\\
\mbox{}\verb@      // Baseline Operations Here @\\
\mbox{}\verb@@\\
\mbox{}\verb@  out1.clear();@\\
\mbox{}\verb@  out2.clear();  @\\
\mbox{}\verb@  out3.clear();@\\
\mbox{}\verb@  defaultItems.clear();@\\
\mbox{}\verb@@\\
\mbox{}\verb@    // End of Baseline Operations@\\
\mbox{}\verb@    ///////////////////////////////@\\
\mbox{}\verb@    } while (tim.check());@\\
\mbox{}\verb@    tim.report(false);@\\
\mbox{}\verb@@\\
\mbox{}\verb@    tim.start(reps, N);@\\
\mbox{}\verb@    do {@\\
\mbox{}\verb@@\\
\mbox{}\verb@    //////////////////////////////  @\\
\mbox{}\verb@      // Baseline Operations Here @\\
\mbox{}\verb@  @\\
\mbox{}\verb@  out1.clear();@\\
\mbox{}\verb@  out2.clear();@\\
\mbox{}\verb@     out3.clear();@\\
\mbox{}\verb@  defaultItems.clear();@\\
\mbox{}\verb@  @\\
\mbox{}\verb@    // End of Baseline Operations@\\
\mbox{}\verb@    ///////////////////////////////@\\
\mbox{}\verb@    // Main Timed Operation@\\
\mbox{}\verb@  r->distribute(v.begin(), v.end());@\\
\mbox{}\verb@    //////////////////////////////////////@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@    while (tim.check());@\\
\mbox{}\verb@    tim.report(false);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@\\
\mbox{}\verb@int main()@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  test();  @\\
\mbox{}\verb@  return 0;@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@
\end{list}
\vspace{-2ex}
\end{flushleft}
\subsection{Test 1c}
\label{sec-code-test1c}

\begin{flushleft} \small \label{part94}
\verb@"timed_test1c.cpp"@ {\footnotesize \hypertarget{114}{114} }$\equiv$
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@#include <cmath>@\\
\mbox{}\verb@#include <cstdlib>@\\
\mbox{}\verb@#include <ctime>@\\
\mbox{}\verb@#include <iostream>@\\
\mbox{}\verb@#include <vector>@\\
\mbox{}\verb@#include <algorithm>@\\
\mbox{}\verb@#include "timer.h"@\\
\mbox{}\verb@#include <iostream>@\\
\mbox{}\verb@#include <vector>@\\
\mbox{}\verb@#include <list>@\\
\mbox{}\verb@#include <iterator>@\\
\mbox{}\verb@@\\
\mbox{}\verb@#include "router.hpp"@\\
\mbox{}\verb@@\\
\mbox{}\verb@using namespace std;@\\
\mbox{}\verb@using std::cout;@\\
\mbox{}\verb@using std::endl;@\\
\mbox{}\verb@using std::vector;@\\
\mbox{}\verb@using std::list;@\\
\mbox{}\verb@using std::back_inserter;@\\
\mbox{}\verb@using std::ostream_iterator;@\\
\mbox{}\verb@using std::back_insert_iterator;@\\
\mbox{}\verb@@\\
\mbox{}\verb@using gdfa::router;@\\
\mbox{}\verb@using gdfa::destination;@\\
\mbox{}\verb@@\\
\mbox{}\verb@template <typename OutputIterator>@\\
\mbox{}\verb@class less_than_n : public destination<int>@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  private:@\\
\mbox{}\verb@    OutputIterator out;@\\
\mbox{}\verb@    int n;@\\
\mbox{}\verb@    @\\
\mbox{}\verb@  public:@\\
\mbox{}\verb@    less_than_n(OutputIterator _out, int _n) : out(_out), n(_n) {}@\\
\mbox{}\verb@    @\\
\mbox{}\verb@    bool distribute(const int& element)@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      if (element < n)@\\
\mbox{}\verb@      {@\\
\mbox{}\verb@        //no output destination@\\
\mbox{}\verb@        return false;//continue filtering@\\
\mbox{}\verb@      }@\\
\mbox{}\verb@      @\\
\mbox{}\verb@      return false;    @\\
\mbox{}\verb@    }@\\
\mbox{}\verb@};@\\
\mbox{}\verb@@\\
\mbox{}\verb@template <typename OutputIterator>@\\
\mbox{}\verb@class my_default : public destination<int>@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  private:@\\
\mbox{}\verb@    OutputIterator out;@\\
\mbox{}\verb@    @\\
\mbox{}\verb@  public:@\\
\mbox{}\verb@    my_default(OutputIterator _out) : out(_out) {}@\\
\mbox{}\verb@    @\\
\mbox{}\verb@    bool distribute(const int& n)@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      //no output destination@\\
\mbox{}\verb@      return true;@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@};@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@void test() {@\\
\mbox{}\verb@  cout << "Test 1c\nTesting N\nTiming distribute on integers.\n";@\\
\mbox{}\verb@  cout<<"Time Decision Making only.  \nFactor out insertion.";@\\
\mbox{}\verb@  cout<<endl;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  srand(time(0));@\\
\mbox{}\verb@@\\
\mbox{}\verb@  // Initial Setup@\\
\mbox{}\verb@  router<int> *r;@\\
\mbox{}\verb@  r = new router<int>;@\\
\mbox{}\verb@  vector<int> v, out1, out2, out3, defaultItems;@\\
\mbox{}\verb@  vector<int> out1_saved, out2_saved, defaultItems_saved;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  typedef std::back_insert_iterator<std::vector<int> > BItype;@\\
\mbox{}\verb@    delete r;@\\
\mbox{}\verb@    r = new router<int>;@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  out1.clear();@\\
\mbox{}\verb@  out2.clear();@\\
\mbox{}\verb@  out3.clear();@\\
\mbox{}\verb@  defaultItems.clear();@\\
\mbox{}\verb@@\\
\mbox{}\verb@  less_than_n<BItype> test1(back_inserter(out1), 1048576);@\\
\mbox{}\verb@  less_than_n<BItype> test2(back_inserter(out2), 1048576);@\\
\mbox{}\verb@  less_than_n<BItype> test3(back_inserter(out3), 1048576);@\\
\mbox{}\verb@  my_default<BItype> defaultTest(back_inserter(defaultItems)); @\\
\mbox{}\verb@  @\\
\mbox{}\verb@  r->add_destination(test1);@\\
\mbox{}\verb@  r->add_destination(test2);@\\
\mbox{}\verb@  r->add_destination(test3);@\\
\mbox{}\verb@  r->set_default(defaultTest);@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@  unsigned long N, N1, N2;@\\
\mbox{}\verb@  unsigned int reps;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  N1 = 1;@\\
\mbox{}\verb@  N2 = 1048576;@\\
\mbox{}\verb@  reps = 10;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  timer tim;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  for (N = N1; N <= N2; N *= 2) {@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@      v.clear(); @\\
\mbox{}\verb@    v.reserve(N);@\\
\mbox{}\verb@    for (int i = 0; i < N; ++i) {@\\
\mbox{}\verb@    v.push_back(i);@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@@\\
\mbox{}\verb@    // Compute the baseline time for N@\\
\mbox{}\verb@    tim.start_baseline(reps);@\\
\mbox{}\verb@    do { @\\
\mbox{}\verb@    //////////////////////////////  @\\
\mbox{}\verb@    // Baseline Operations Here @\\
\mbox{}\verb@    out1.clear();@\\
\mbox{}\verb@    out2.clear();  @\\
\mbox{}\verb@    out3.clear();@\\
\mbox{}\verb@    defaultItems.clear();@\\
\mbox{}\verb@@\\
\mbox{}\verb@    // End of Baseline Operations@\\
\mbox{}\verb@    ///////////////////////////////@\\
\mbox{}\verb@    } while (tim.check());@\\
\mbox{}\verb@    tim.report(false);@\\
\mbox{}\verb@@\\
\mbox{}\verb@    tim.start(reps, N);@\\
\mbox{}\verb@    do {@\\
\mbox{}\verb@@\\
\mbox{}\verb@    //////////////////////////////  @\\
\mbox{}\verb@    // Baseline Operations Here @\\
\mbox{}\verb@    out1.clear();@\\
\mbox{}\verb@    out2.clear();@\\
\mbox{}\verb@       out3.clear();@\\
\mbox{}\verb@    defaultItems.clear();@\\
\mbox{}\verb@    // End of Baseline Operations@\\
\mbox{}\verb@    ///////////////////////////////@\\
\mbox{}\verb@    // Main Timed Operation@\\
\mbox{}\verb@    r->distribute(v.begin(), v.end());@\\
\mbox{}\verb@    //////////////////////////////////////@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@    while (tim.check());@\\
\mbox{}\verb@    tim.report(false);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@\\
\mbox{}\verb@int main()@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  test();  @\\
\mbox{}\verb@  return 0;@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@
\end{list}
\vspace{-2ex}
\end{flushleft}
\section{Test 2}
\subsection{Test 2a}
\label{sec-code-test2a}

\begin{flushleft} \small \label{part95}
\verb@"timed_test2a.cpp"@ {\footnotesize \hypertarget{118}{118} }$\equiv$
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@#include <cmath>@\\
\mbox{}\verb@#include <cstdlib>@\\
\mbox{}\verb@#include <ctime>@\\
\mbox{}\verb@#include <iostream>@\\
\mbox{}\verb@#include <vector>@\\
\mbox{}\verb@#include <algorithm>@\\
\mbox{}\verb@#include "timer.h"@\\
\mbox{}\verb@#include <iostream>@\\
\mbox{}\verb@#include <vector>@\\
\mbox{}\verb@#include <list>@\\
\mbox{}\verb@#include <iterator>@\\
\mbox{}\verb@@\\
\mbox{}\verb@#include "router.hpp"@\\
\mbox{}\verb@@\\
\mbox{}\verb@using namespace std;@\\
\mbox{}\verb@using std::cout;@\\
\mbox{}\verb@using std::endl;@\\
\mbox{}\verb@using std::vector;@\\
\mbox{}\verb@using std::list;@\\
\mbox{}\verb@using std::back_inserter;@\\
\mbox{}\verb@using std::ostream_iterator;@\\
\mbox{}\verb@using std::back_insert_iterator;@\\
\mbox{}\verb@@\\
\mbox{}\verb@using gdfa::router;@\\
\mbox{}\verb@using gdfa::destination;@\\
\mbox{}\verb@@\\
\mbox{}\verb@template <typename OutputIterator>@\\
\mbox{}\verb@class less_than_n : public destination<int>@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  private:@\\
\mbox{}\verb@    OutputIterator out;@\\
\mbox{}\verb@    int n;@\\
\mbox{}\verb@    @\\
\mbox{}\verb@  public:@\\
\mbox{}\verb@    less_than_n(OutputIterator _out, int _n) : out(_out), n(_n) {}@\\
\mbox{}\verb@    @\\
\mbox{}\verb@    bool distribute(const int& element)@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      if (element < n)@\\
\mbox{}\verb@      {@\\
\mbox{}\verb@        *(out++) = element;@\\
\mbox{}\verb@        return false;// continue filtering@\\
\mbox{}\verb@      }@\\
\mbox{}\verb@      @\\
\mbox{}\verb@      return false;    @\\
\mbox{}\verb@    }@\\
\mbox{}\verb@};@\\
\mbox{}\verb@@\\
\mbox{}\verb@template <typename OutputIterator>@\\
\mbox{}\verb@class my_default : public destination<int>@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  private:@\\
\mbox{}\verb@    OutputIterator out;@\\
\mbox{}\verb@    @\\
\mbox{}\verb@  public:@\\
\mbox{}\verb@    my_default(OutputIterator _out) : out(_out) {}@\\
\mbox{}\verb@    @\\
\mbox{}\verb@    bool distribute(const int& n)@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      *(out) = n;@\\
\mbox{}\verb@      return true;@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@};@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@void test2() {@\\
\mbox{}\verb@  cout << "Test 2a\nTesting M\nTiming distribute on integers.\n";@\\
\mbox{}\verb@  cout << "Distribute to all destinations." << endl;@\\
\mbox{}\verb@  srand(time(0));@\\
\mbox{}\verb@@\\
\mbox{}\verb@  // Initial Setup@\\
\mbox{}\verb@  router<int> *r;@\\
\mbox{}\verb@  r = new router<int>;@\\
\mbox{}\verb@  vector<int> v, out1, out2, defaultItems;@\\
\mbox{}\verb@  vector<int> out1_saved, out2_saved, defaultItems_saved;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  typedef std::back_insert_iterator<std::vector<int> > BItype;@\\
\mbox{}\verb@    delete r;@\\
\mbox{}\verb@    r = new router<int>;@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  out1.clear();@\\
\mbox{}\verb@  out2.clear();@\\
\mbox{}\verb@  defaultItems.clear();@\\
\mbox{}\verb@@\\
\mbox{}\verb@  less_than_n<BItype> test1048576(back_inserter(out1), 1048576);@\\
\mbox{}\verb@  less_than_n<BItype> test20(back_inserter(out2), 20);@\\
\mbox{}\verb@  my_default<BItype> defaultTest(back_inserter(defaultItems)); @\\
\mbox{}\verb@  @\\
\mbox{}\verb@  r->set_default(defaultTest);@\\
\mbox{}\verb@      v.clear(); @\\
\mbox{}\verb@    v.reserve(10);@\\
\mbox{}\verb@    for (int i = 0; i < 10; ++i) {@\\
\mbox{}\verb@    v.push_back(i);@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@  unsigned long N, N1, N2;@\\
\mbox{}\verb@  unsigned int reps;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  N1 = 1;@\\
\mbox{}\verb@  N2 = 1048576;@\\
\mbox{}\verb@  reps = 10;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  timer tim;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  for (N = N1; N <= N2; N *= 2) {@\\
\mbox{}\verb@@\\
\mbox{}\verb@    for (int i = 0; i < (N/2); ++i) {@\\
\mbox{}\verb@    r->add_destination(test1048576);@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@    // Compute the baseline time for N@\\
\mbox{}\verb@    tim.start_baseline(reps);@\\
\mbox{}\verb@    do { @\\
\mbox{}\verb@    //////////////////////////////  @\\
\mbox{}\verb@      // Baseline Operations Here @\\
\mbox{}\verb@    out1.clear();@\\
\mbox{}\verb@    defaultItems.clear();@\\
\mbox{}\verb@      @\\
\mbox{}\verb@    // End of Baseline Operations@\\
\mbox{}\verb@    //////////////////////////////@\\
\mbox{}\verb@    } while (tim.check());@\\
\mbox{}\verb@    tim.report(false);@\\
\mbox{}\verb@@\\
\mbox{}\verb@    tim.start(reps, N);@\\
\mbox{}\verb@    do {@\\
\mbox{}\verb@@\\
\mbox{}\verb@    //////////////////////////////  @\\
\mbox{}\verb@      // Baseline Operations Here @\\
\mbox{}\verb@    out1.clear();@\\
\mbox{}\verb@    defaultItems.clear();@\\
\mbox{}\verb@           @\\
\mbox{}\verb@    // End of Baseline Operations@\\
\mbox{}\verb@    ///////////////////////////////@\\
\mbox{}\verb@    // Main Timed Operation@\\
\mbox{}\verb@  r->distribute(v.begin(), v.end());@\\
\mbox{}\verb@    //////////////////////////////////////@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@    while (tim.check());@\\
\mbox{}\verb@    tim.report(false);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@\\
\mbox{}\verb@int main()@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  test2();  @\\
\mbox{}\verb@  return 0;@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@
\end{list}
\vspace{-2ex}
\end{flushleft}
\subsection{Test 2b}
\label{sec-code-test2b}

\begin{flushleft} \small \label{part96}
\verb@"timed_test2b.cpp"@ {\footnotesize \hypertarget{121}{121} }$\equiv$
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@#include <cmath>@\\
\mbox{}\verb@#include <cstdlib>@\\
\mbox{}\verb@#include <ctime>@\\
\mbox{}\verb@#include <iostream>@\\
\mbox{}\verb@#include <vector>@\\
\mbox{}\verb@#include <algorithm>@\\
\mbox{}\verb@#include "timer.h"@\\
\mbox{}\verb@#include <iostream>@\\
\mbox{}\verb@#include <vector>@\\
\mbox{}\verb@#include <list>@\\
\mbox{}\verb@#include <iterator>@\\
\mbox{}\verb@@\\
\mbox{}\verb@#include "router.hpp"@\\
\mbox{}\verb@@\\
\mbox{}\verb@using namespace std;@\\
\mbox{}\verb@using std::cout;@\\
\mbox{}\verb@using std::endl;@\\
\mbox{}\verb@using std::vector;@\\
\mbox{}\verb@using std::list;@\\
\mbox{}\verb@using std::back_inserter;@\\
\mbox{}\verb@using std::ostream_iterator;@\\
\mbox{}\verb@using std::back_insert_iterator;@\\
\mbox{}\verb@@\\
\mbox{}\verb@using gdfa::router;@\\
\mbox{}\verb@using gdfa::destination;@\\
\mbox{}\verb@@\\
\mbox{}\verb@template <typename OutputIterator>@\\
\mbox{}\verb@class less_than_n : public destination<int>@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  private:@\\
\mbox{}\verb@    OutputIterator out;@\\
\mbox{}\verb@    int n;@\\
\mbox{}\verb@    @\\
\mbox{}\verb@  public:@\\
\mbox{}\verb@    less_than_n(OutputIterator _out, int _n) : out(_out), n(_n) {}@\\
\mbox{}\verb@    @\\
\mbox{}\verb@    bool distribute(const int& element)@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      if (element > n)@\\
\mbox{}\verb@      {@\\
\mbox{}\verb@        *(out++) = element;@\\
\mbox{}\verb@        return false;// continue filtering@\\
\mbox{}\verb@      }@\\
\mbox{}\verb@      @\\
\mbox{}\verb@      return false;    @\\
\mbox{}\verb@    }@\\
\mbox{}\verb@};@\\
\mbox{}\verb@@\\
\mbox{}\verb@template <typename OutputIterator>@\\
\mbox{}\verb@class my_default : public destination<int>@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  private:@\\
\mbox{}\verb@    OutputIterator out;@\\
\mbox{}\verb@    @\\
\mbox{}\verb@  public:@\\
\mbox{}\verb@    my_default(OutputIterator _out) : out(_out) {}@\\
\mbox{}\verb@    @\\
\mbox{}\verb@    bool distribute(const int& n)@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      *(out) = n;@\\
\mbox{}\verb@      return true;@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@};@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@void test2() {@\\
\mbox{}\verb@  cout << "Test 2b\nTesting M\nTiming distribute on integers.\n";@\\
\mbox{}\verb@  cout << "Distribute to just 1 of the destinations." << endl;@\\
\mbox{}\verb@  srand(time(0));@\\
\mbox{}\verb@@\\
\mbox{}\verb@  // Initial Setup@\\
\mbox{}\verb@  router<int> *r;@\\
\mbox{}\verb@  r = new router<int>;@\\
\mbox{}\verb@  vector<int> v, out1, out2, defaultItems;@\\
\mbox{}\verb@  vector<int> out1_saved, out2_saved, defaultItems_saved;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  typedef std::back_insert_iterator<std::vector<int> > BItype;@\\
\mbox{}\verb@    delete r;@\\
\mbox{}\verb@    r = new router<int>;@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  out1.clear();@\\
\mbox{}\verb@  out2.clear();@\\
\mbox{}\verb@  defaultItems.clear();@\\
\mbox{}\verb@@\\
\mbox{}\verb@  less_than_n<BItype> test1048576(back_inserter(out1), 1048576);@\\
\mbox{}\verb@  less_than_n<BItype> test20(back_inserter(out2), 20);@\\
\mbox{}\verb@  my_default<BItype> defaultTest(back_inserter(defaultItems)); @\\
\mbox{}\verb@  @\\
\mbox{}\verb@  r->set_default(defaultTest);@\\
\mbox{}\verb@      v.clear(); @\\
\mbox{}\verb@    v.reserve(10);@\\
\mbox{}\verb@//    for (int i = 0; i < 100; ++i) {@\\
\mbox{}\verb@    for (int i = 0; i < 10; ++i) {@\\
\mbox{}\verb@    v.push_back(i);@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@  unsigned long N, N1, N2;@\\
\mbox{}\verb@  unsigned int reps;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  N1 = 1;@\\
\mbox{}\verb@  N2 = 1048576;@\\
\mbox{}\verb@  reps = 10;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  timer tim;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  for (N = N1; N <= N2; N *= 2) {@\\
\mbox{}\verb@@\\
\mbox{}\verb@    for (int i = 0; i < (N/2); ++i) {@\\
\mbox{}\verb@    r->add_destination(test1048576);@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@    // Compute the baseline time for N@\\
\mbox{}\verb@    tim.start_baseline(reps);@\\
\mbox{}\verb@    do { @\\
\mbox{}\verb@    //////////////////////////////  @\\
\mbox{}\verb@      // Baseline Operations Here @\\
\mbox{}\verb@    out1.clear();@\\
\mbox{}\verb@    defaultItems.clear();@\\
\mbox{}\verb@      @\\
\mbox{}\verb@    // End of Baseline Operations@\\
\mbox{}\verb@    //////////////////////////////@\\
\mbox{}\verb@    } while (tim.check());@\\
\mbox{}\verb@    tim.report(false);@\\
\mbox{}\verb@@\\
\mbox{}\verb@    tim.start(reps, N);@\\
\mbox{}\verb@    do {@\\
\mbox{}\verb@@\\
\mbox{}\verb@    //////////////////////////////  @\\
\mbox{}\verb@      // Baseline Operations Here @\\
\mbox{}\verb@    out1.clear();@\\
\mbox{}\verb@    defaultItems.clear();@\\
\mbox{}\verb@           @\\
\mbox{}\verb@    // End of Baseline Operations@\\
\mbox{}\verb@    ///////////////////////////////@\\
\mbox{}\verb@    // Main Timed Operation@\\
\mbox{}\verb@  r->distribute(v.begin(), v.end());@\\
\mbox{}\verb@    //////////////////////////////////////@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@    while (tim.check());@\\
\mbox{}\verb@    tim.report(false);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@\\
\mbox{}\verb@int main()@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  test2();  @\\
\mbox{}\verb@  return 0;@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@
\end{list}
\vspace{-2ex}
\end{flushleft}
\subsection{Test 2c}
\label{sec-code-test2c}

\begin{flushleft} \small \label{part97}
\verb@"timed_test2c.cpp"@ {\footnotesize \hypertarget{124}{124} }$\equiv$
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@#include <cmath>@\\
\mbox{}\verb@#include <cstdlib>@\\
\mbox{}\verb@#include <ctime>@\\
\mbox{}\verb@#include <iostream>@\\
\mbox{}\verb@#include <vector>@\\
\mbox{}\verb@#include <algorithm>@\\
\mbox{}\verb@#include "timer.h"@\\
\mbox{}\verb@#include <iostream>@\\
\mbox{}\verb@#include <vector>@\\
\mbox{}\verb@#include <list>@\\
\mbox{}\verb@#include <iterator>@\\
\mbox{}\verb@@\\
\mbox{}\verb@#include "router.hpp"@\\
\mbox{}\verb@@\\
\mbox{}\verb@using namespace std;@\\
\mbox{}\verb@using std::cout;@\\
\mbox{}\verb@using std::endl;@\\
\mbox{}\verb@using std::vector;@\\
\mbox{}\verb@using std::list;@\\
\mbox{}\verb@using std::back_inserter;@\\
\mbox{}\verb@using std::ostream_iterator;@\\
\mbox{}\verb@using std::back_insert_iterator;@\\
\mbox{}\verb@@\\
\mbox{}\verb@using gdfa::router;@\\
\mbox{}\verb@using gdfa::destination;@\\
\mbox{}\verb@@\\
\mbox{}\verb@template <typename OutputIterator>@\\
\mbox{}\verb@class less_than_n : public destination<int>@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  private:@\\
\mbox{}\verb@    OutputIterator out;@\\
\mbox{}\verb@    int n;@\\
\mbox{}\verb@    @\\
\mbox{}\verb@  public:@\\
\mbox{}\verb@    less_than_n(OutputIterator _out, int _n) : out(_out), n(_n) {}@\\
\mbox{}\verb@    @\\
\mbox{}\verb@    bool distribute(const int& element)@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      if (element < n)@\\
\mbox{}\verb@      {        @\\
\mbox{}\verb@        //no output destination@\\
\mbox{}\verb@        return false;// continue filtering@\\
\mbox{}\verb@      }@\\
\mbox{}\verb@      @\\
\mbox{}\verb@      return false;    @\\
\mbox{}\verb@    }@\\
\mbox{}\verb@};@\\
\mbox{}\verb@@\\
\mbox{}\verb@template <typename OutputIterator>@\\
\mbox{}\verb@class my_default : public destination<int>@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  private:@\\
\mbox{}\verb@    OutputIterator out;@\\
\mbox{}\verb@    @\\
\mbox{}\verb@  public:@\\
\mbox{}\verb@    my_default(OutputIterator _out) : out(_out) {}@\\
\mbox{}\verb@    @\\
\mbox{}\verb@    bool distribute(const int& n)@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      //no output destination@\\
\mbox{}\verb@      return true;@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@};@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@void test2() {@\\
\mbox{}\verb@  cout << "Test 2c\nTesting M\nTiming distribute on integers.\n";@\\
\mbox{}\verb@  cout<<"Time Decision Making only.  \nFactor out insertion.";@\\
\mbox{}\verb@  cout<<endl;@\\
\mbox{}\verb@  srand(time(0));@\\
\mbox{}\verb@@\\
\mbox{}\verb@  // Initial Setup@\\
\mbox{}\verb@  router<int> *r;@\\
\mbox{}\verb@  r = new router<int>;@\\
\mbox{}\verb@  vector<int> v, out1, out2, defaultItems;@\\
\mbox{}\verb@  vector<int> out1_saved, out2_saved, defaultItems_saved;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  typedef std::back_insert_iterator<std::vector<int> > BItype;@\\
\mbox{}\verb@    delete r;@\\
\mbox{}\verb@    r = new router<int>;@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  out1.clear();@\\
\mbox{}\verb@  out2.clear();@\\
\mbox{}\verb@  defaultItems.clear();@\\
\mbox{}\verb@@\\
\mbox{}\verb@  less_than_n<BItype> test1048576(back_inserter(out1), 1048576);@\\
\mbox{}\verb@  less_than_n<BItype> test20(back_inserter(out2), 20);@\\
\mbox{}\verb@  my_default<BItype> defaultTest(back_inserter(defaultItems)); @\\
\mbox{}\verb@  @\\
\mbox{}\verb@  r->set_default(defaultTest);@\\
\mbox{}\verb@      v.clear(); @\\
\mbox{}\verb@    v.reserve(10);@\\
\mbox{}\verb@    for (int i = 0; i < 10; ++i) {@\\
\mbox{}\verb@    v.push_back(i);@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@  unsigned long N, N1, N2;@\\
\mbox{}\verb@  unsigned int reps;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  N1 = 1;@\\
\mbox{}\verb@  N2 = 1048576;@\\
\mbox{}\verb@  reps = 10;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  timer tim;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  for (N = N1; N <= N2; N *= 2) {@\\
\mbox{}\verb@@\\
\mbox{}\verb@    for (int i = 0; i < (N/2); ++i) {@\\
\mbox{}\verb@    r->add_destination(test1048576);@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@    // Compute the baseline time for N@\\
\mbox{}\verb@    tim.start_baseline(reps);@\\
\mbox{}\verb@    do { @\\
\mbox{}\verb@    //////////////////////////////  @\\
\mbox{}\verb@      // Baseline Operations Here @\\
\mbox{}\verb@    //out1.clear();@\\
\mbox{}\verb@    //defaultItems.clear();@\\
\mbox{}\verb@      @\\
\mbox{}\verb@    // End of Baseline Operations@\\
\mbox{}\verb@    //////////////////////////////@\\
\mbox{}\verb@    } while (tim.check());@\\
\mbox{}\verb@    tim.report(false);@\\
\mbox{}\verb@@\\
\mbox{}\verb@    tim.start(reps, N);@\\
\mbox{}\verb@    do {@\\
\mbox{}\verb@@\\
\mbox{}\verb@    //////////////////////////////  @\\
\mbox{}\verb@      // Baseline Operations Here @\\
\mbox{}\verb@    //out1.clear();@\\
\mbox{}\verb@    //defaultItems.clear();@\\
\mbox{}\verb@           @\\
\mbox{}\verb@    // End of Baseline Operations@\\
\mbox{}\verb@    ///////////////////////////////@\\
\mbox{}\verb@    // Main Timed Operation@\\
\mbox{}\verb@  r->distribute(v.begin(), v.end());@\\
\mbox{}\verb@    //////////////////////////////////////@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@    while (tim.check());@\\
\mbox{}\verb@    tim.report(false);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@\\
\mbox{}\verb@int main()@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  test2();  @\\
\mbox{}\verb@  return 0;@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@
\end{list}
\vspace{-2ex}
\end{flushleft}
\section{Test 3}
\label{sec-code-test3}

\begin{flushleft} \small \label{part98}
\verb@"timed_test3.cpp"@ {\footnotesize \hypertarget{127}{127} }$\equiv$
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@#include <cmath>@\\
\mbox{}\verb@#include <cstdlib>@\\
\mbox{}\verb@#include <ctime>@\\
\mbox{}\verb@#include <iostream>@\\
\mbox{}\verb@#include <vector>@\\
\mbox{}\verb@#include <algorithm>@\\
\mbox{}\verb@#include "timer.h"@\\
\mbox{}\verb@#include <iostream>@\\
\mbox{}\verb@#include <vector>@\\
\mbox{}\verb@#include <list>@\\
\mbox{}\verb@#include <iterator>@\\
\mbox{}\verb@@\\
\mbox{}\verb@#include "router.hpp"@\\
\mbox{}\verb@@\\
\mbox{}\verb@using namespace std;@\\
\mbox{}\verb@using std::cout;@\\
\mbox{}\verb@using std::endl;@\\
\mbox{}\verb@using std::vector;@\\
\mbox{}\verb@using std::list;@\\
\mbox{}\verb@using std::back_inserter;@\\
\mbox{}\verb@using std::ostream_iterator;@\\
\mbox{}\verb@using std::back_insert_iterator;@\\
\mbox{}\verb@@\\
\mbox{}\verb@using gdfa::router;@\\
\mbox{}\verb@using gdfa::destination;@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@bool less_than_n(const int& element) {@\\
\mbox{}\verb@      if (element < 1048576) {@\\
\mbox{}\verb@        return true;@\\
\mbox{}\verb@      }@\\
\mbox{}\verb@      @\\
\mbox{}\verb@      return false;    @\\
\mbox{}\verb@}@\\
\mbox{}\verb@@\\
\mbox{}\verb@    @\\
\mbox{}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@void test() {@\\
\mbox{}\verb@  cout << "Test 3\nSimple Version of Distribute\nTesting N\n";@\\
\mbox{}\verb@  cout << "Timing distribute on integers." << endl;@\\
\mbox{}\verb@  srand(time(0));@\\
\mbox{}\verb@@\\
\mbox{}\verb@  // Initial Setup@\\
\mbox{}\verb@  vector<int> v, out1, defaultItems;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  typedef std::back_insert_iterator<std::vector<int> > BItype;@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  out1.clear();@\\
\mbox{}\verb@  defaultItems.clear();@\\
\mbox{}\verb@@\\
\mbox{}\verb@  unsigned long N, N1, N2;@\\
\mbox{}\verb@  unsigned int reps;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  N1 = 1;@\\
\mbox{}\verb@  N2 = 1048576;@\\
\mbox{}\verb@  reps = 10;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  timer tim;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  for (N = N1; N <= N2; N *= 2) {@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@      v.clear(); @\\
\mbox{}\verb@    v.reserve(N);@\\
\mbox{}\verb@    for (int i = 0; i < N; ++i) {@\\
\mbox{}\verb@    v.push_back(i);@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@@\\
\mbox{}\verb@    // Compute the baseline time for N@\\
\mbox{}\verb@    tim.start_baseline(reps);@\\
\mbox{}\verb@    do { @\\
\mbox{}\verb@    //////////////////////////////  @\\
\mbox{}\verb@    // Baseline Operations Here @\\
\mbox{}\verb@    out1.clear();@\\
\mbox{}\verb@    defaultItems.clear();@\\
\mbox{}\verb@    // End of Baseline Operations@\\
\mbox{}\verb@    ///////////////////////////////@\\
\mbox{}\verb@    } while (tim.check());@\\
\mbox{}\verb@    tim.report(false);@\\
\mbox{}\verb@@\\
\mbox{}\verb@    tim.start(reps, N);@\\
\mbox{}\verb@    do {@\\
\mbox{}\verb@@\\
\mbox{}\verb@    //////////////////////////////  @\\
\mbox{}\verb@    // Baseline Operations Here @\\
\mbox{}\verb@    out1.clear();@\\
\mbox{}\verb@    defaultItems.clear();@\\
\mbox{}\verb@    // End of Baseline Operations@\\
\mbox{}\verb@    ///////////////////////////////@\\
\mbox{}\verb@    // Main Timed Operation@\\
\mbox{}\verb@    gdfa::distribute(v.begin(), v.end(), back_inserter(out1), @\\
\mbox{}\verb@    back_inserter(defaultItems), less_than_n);@\\
\mbox{}\verb@    //////////////////////////////////////@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@    while (tim.check());@\\
\mbox{}\verb@    tim.report(false);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@\\
\mbox{}\verb@int main()@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  test();  @\\
\mbox{}\verb@  return 0;@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@
\end{list}
\vspace{-2ex}
\end{flushleft}
\section{Auxiliary Code}
The following code is taken from \cite{drm-book} and was used by the 
test code in Sections \ref{sec-code-test1a}-\ref{sec-code-test3}.

\begin{flushleft} \small \label{part99}
\verb@"timer.h"@ {\footnotesize \hypertarget{129}{129} }$\equiv$
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@// Define a timer class for analyzing algorithm performance.@\\
\mbox{}\verb@#include <iostream>@\\
\mbox{}\verb@#include <iomanip>@\\
\mbox{}\verb@#include <vector>@\\
\mbox{}\verb@#include <map>@\\
\mbox{}\verb@#include <algorithm>@\\
\mbox{}\verb@using namespace std;@\\
\mbox{}\verb@@\\
\mbox{}\verb@class timer {@\\
\mbox{}\verb@public:@\\
\mbox{}\verb@  timer();  // Default constructor@\\
\mbox{}\verb@  // Start a series of r trials for problem size N:@\\
\mbox{}\verb@  void start(unsigned int r, unsigned long N);@\\
\mbox{}\verb@  // Start a series of r trials to determine baseline time:@\\
\mbox{}\verb@  void start_baseline(unsigned int r);@\\
\mbox{}\verb@  // Returns true if the trials have been completed, else false@\\
\mbox{}\verb@  bool check();@\\
\mbox{}\verb@  // Report the results of the trials on cout@\\
\mbox{}\verb@  // with additional output if verbose is true:@\\
\mbox{}\verb@  void report(bool verbose);@\\
\mbox{}\verb@  // Returns the results for external use@\\
\mbox{}\verb@  const map<unsigned int, double>& results() const;@\\
\mbox{}\verb@@\\
\mbox{}\verb@private:@\\
\mbox{}\verb@  unsigned int reps;  // Number of trials@\\
\mbox{}\verb@  // For storing loop iterations of a trial@\\
\mbox{}\verb@  vector<long> iterations;@\\
\mbox{}\verb@  // For saving initial and final times of a trial@\\
\mbox{}\verb@  time_t initial, final;@\\
\mbox{}\verb@  // For counting loop iterations of a trial@\\
\mbox{}\verb@  unsigned long count;@\\
\mbox{}\verb@  // For saving the problem size (N) for current trials@\\
\mbox{}\verb@  unsigned int problem_size;@\\
\mbox{}\verb@  // For storing (problem size, time) pairs@\\
\mbox{}\verb@  map<unsigned int, double> result_map;@\\
\mbox{}\verb@  // true if this is a baseline computation, false otherwise@\\
\mbox{}\verb@  bool baseline;@\\
\mbox{}\verb@  // For recording the baseline time @\\
\mbox{}\verb@  double baseline_time;@\\
\mbox{}\verb@};@\\
\mbox{}\verb@@\\
\mbox{}\verb@timer::timer() { baseline = false; }@\\
\mbox{}\verb@void timer::start(unsigned int r, unsigned long N) @\\
\mbox{}\verb@{@\\
\mbox{}\verb@  reps = r;@\\
\mbox{}\verb@  problem_size = N;@\\
\mbox{}\verb@  count = 0;@\\
\mbox{}\verb@  iterations.clear();@\\
\mbox{}\verb@  iterations.reserve(reps);@\\
\mbox{}\verb@  initial = time(0);@\\
\mbox{}\verb@}@\\
\mbox{}\verb@void timer::start_baseline(unsigned int r) @\\
\mbox{}\verb@{@\\
\mbox{}\verb@  baseline = true;@\\
\mbox{}\verb@  start(r, 0);@\\
\mbox{}\verb@}@\\
\mbox{}\verb@bool timer::check() @\\
\mbox{}\verb@{@\\
\mbox{}\verb@  ++count;@\\
\mbox{}\verb@  final = time(0);@\\
\mbox{}\verb@  if (initial < final) {@\\
\mbox{}\verb@    iterations.push_back(count);  @\\
\mbox{}\verb@    initial = final;@\\
\mbox{}\verb@    count = 0;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  return (iterations.size() < reps);@\\
\mbox{}\verb@}@\\
\mbox{}\verb@void timer::report(bool verbose)@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  if (verbose) {@\\
\mbox{}\verb@    for (unsigned int k = 0; k < iterations.size(); ++k) {@\\
\mbox{}\verb@      cout << iterations[k] << " ";@\\
\mbox{}\verb@      if ((k+1) % 10 == 0)@\\
\mbox{}\verb@        cout << endl;@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@    cout << endl;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  sort(iterations.begin(), iterations.end());@\\
\mbox{}\verb@  if (verbose) {@\\
\mbox{}\verb@    cout << "Sorted counts:" << endl;@\\
\mbox{}\verb@    for (unsigned int k = 0; k < iterations.size(); ++k) {@\\
\mbox{}\verb@      cout << iterations[k] << " ";@\\
\mbox{}\verb@      if ((k+1) % 10 == 0)@\\
\mbox{}\verb@        cout << endl;@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@    cout << endl;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@@\\
\mbox{}\verb@  int selected_count = iterations[reps/2];@\\
\mbox{}\verb@  if (verbose) @\\
\mbox{}\verb@    cout << "Selected count: " << selected_count << endl;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  if (baseline) {@\\
\mbox{}\verb@    baseline_time = 1000.0/selected_count;@\\
\mbox{}\verb@    cout << "Baseline time: " << baseline_time << endl;@\\
\mbox{}\verb@    baseline = false;@\\
\mbox{}\verb@  } else {@\\
\mbox{}\verb@    double calculated_time, growth_factor;@\\
\mbox{}\verb@    result_map[problem_size] = calculated_time = @\\
\mbox{}\verb@      1000.0/selected_count - baseline_time;@\\
\mbox{}\verb@    cout << setiosflags(ios::fixed) << setprecision(4)@\\
\mbox{}\verb@         << setw(35) << problem_size << setw(12)@\\
\mbox{}\verb@         << calculated_time << " ms ";@\\
\mbox{}\verb@    if (result_map.find(problem_size/2) != result_map.end()) {@\\
\mbox{}\verb@      growth_factor = calculated_time / result_map[problem_size/2];@\\
\mbox{}\verb@      cout << setiosflags(ios::fixed) << setprecision(4) @\\
\mbox{}\verb@           << setw(8) << growth_factor;@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@    cout << endl;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@}@\\
\mbox{}\verb@const map<unsigned int, double>& timer::results() const@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  return result_map;@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@
\end{list}
\vspace{-2ex}
\end{flushleft}
\chapter{Code for Operation Counting Tests}
\section{Operation Counting Iterator Adapters}
\label{sec-code-counters}
\begin{flushleft} \small \label{part100}
\verb@"counters.h"@ {\footnotesize \hypertarget{133}{133} }$\equiv$
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@#ifndef COUNTERS_H@\\
\mbox{}\verb@#define COUNTERS_H@\\
\mbox{}\verb@@\\
\mbox{}\verb@#include <iostream>@\\
\mbox{}\verb@#include <iomanip>@\\
\mbox{}\verb@#include <string>@\\
\mbox{}\verb@#include <typeinfo>@\\
\mbox{}\verb@#include <algorithm>@\\
\mbox{}\verb@#include <functional>@\\
\mbox{}\verb@#include <numeric>@\\
\mbox{}\verb@#include <map>@\\
\mbox{}\verb@#include <vector>@\\
\mbox{}\verb@#include <stack>@\\
\mbox{}\verb@#include <utility>@\\
\mbox{}\verb@@\\
\mbox{}\verb@#include <boost/iterator_adaptors.hpp>@\\
\mbox{}\verb@@\\
\mbox{}\verb@namespace counters {@\\
\mbox{}\verb@@\\
\mbox{}\verb@#ifndef DEFAULT_COUNTER_TYPE@\\
\mbox{}\verb@#  define DEFAULT_COUNTER_TYPE unsigned long@\\
\mbox{}\verb@#endif@\\
\mbox{}\verb@@\\
\mbox{}\verb@enum operator_type {@\\
\mbox{}\verb@  DEFAULT_CTOR, COPY_CTOR, @\\
\mbox{}\verb@  OTHER_CTOR, BASE, DTOR, GENERATION,@\\
\mbox{}\verb@  ASSIGNMENT, CONVERSION, LESS_THAN, EQUALITY,@\\
\mbox{}\verb@  POST_INCREMENT, PRE_INCREMENT, @\\
\mbox{}\verb@  POST_DECREMENT, PRE_DECREMENT, @\\
\mbox{}\verb@  UNARY_PLUS, UNARY_MINUS, PLUS, MINUS, TIMES, DIVIDE, MODULO,@\\
\mbox{}\verb@  LEFT_SHIFT, RIGHT_SHIFT,@\\
\mbox{}\verb@  PLUS_ASSIGN, MINUS_ASSIGN, @\\
\mbox{}\verb@  TIMES_ASSIGN, DIVIDE_ASSIGN, MODULO_ASSIGN,@\\
\mbox{}\verb@  LEFT_SHIFT_ASSIGN, RIGHT_SHIFT_ASSIGN,@\\
\mbox{}\verb@  DEREFERENCE, MEMBER, SUBSCRIPT, FUNCTION_CALL,@\\
\mbox{}\verb@  NEGATE, AND, AND_ASSIGN, OR, OR_ASSIGN, XOR, XOR_ASSIGN,@\\
\mbox{}\verb@  NCOUNTERS,@\\
\mbox{}\verb@};@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@struct default_recorder_visitor {@\\
\mbox{}\verb@@\\
\mbox{}\verb@  template <typename ForwardIterator>@\\
\mbox{}\verb@  typename std::iterator_traits<ForwardIterator>::value_type@\\
\mbox{}\verb@    choose_element(const ForwardIterator& first, @\\
\mbox{}\verb@                   const ForwardIterator& last) const {@\\
\mbox{}\verb@@\\
\mbox{}\verb@    typedef @\\
\mbox{}\verb@        typename std::iterator_traits<ForwardIterator>@\\
\mbox{}\verb@                ::value_type T;@\\
\mbox{}\verb@@\\
\mbox{}\verb@    // because nth_element is mutative, we must copy the range @\\
\mbox{}\verb@    // to a temporary container.@\\
\mbox{}\verb@    std::vector<T> tmp(first, last);@\\
\mbox{}\verb@  @\\
\mbox{}\verb@    typename std::vector<T>::iterator midpoint = tmp.begin() + @\\
\mbox{}\verb@                                          tmp.size() / 2;@\\
\mbox{}\verb@    std::nth_element(tmp.begin(), midpoint, tmp.end());@\\
\mbox{}\verb@@\\
\mbox{}\verb@    // OK, now find the midpoint value in the original @\\
\mbox{}\verb@    // container and return that iterator.@\\
\mbox{}\verb@    return *std::find(first, last, *midpoint);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@@\\
\mbox{}\verb@  template <typename ForwardIterator>@\\
\mbox{}\verb@  ForwardIterator transmute(ForwardIterator first, @\\
\mbox{}\verb@                            ForwardIterator last) const {@\\
\mbox{}\verb@    return last;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@};@\\
\mbox{}\verb@template <typename Base = default_recorder_visitor>@\\
\mbox{}\verb@struct min_element_recorder_visitor : public Base {@\\
\mbox{}\verb@@\\
\mbox{}\verb@  template <typename ForwardIterator>@\\
\mbox{}\verb@  typename std::iterator_traits<ForwardIterator>::value_type@\\
\mbox{}\verb@    choose_element(ForwardIterator first, @\\
\mbox{}\verb@                   ForwardIterator last) const {@\\
\mbox{}\verb@    return *std::min_element(first, last);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@};@\\
\mbox{}\verb@template <typename Base = default_recorder_visitor>@\\
\mbox{}\verb@struct max_element_recorder_visitor : public Base {@\\
\mbox{}\verb@@\\
\mbox{}\verb@  template <typename ForwardIterator>@\\
\mbox{}\verb@  typename std::iterator_traits<ForwardIterator>::value_type@\\
\mbox{}\verb@    choose_element(ForwardIterator first, @\\
\mbox{}\verb@                   ForwardIterator last) const {@\\
\mbox{}\verb@    return *std::max_element(first, last);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@};@\\
\mbox{}\verb@template <typename Base = default_recorder_visitor>@\\
\mbox{}\verb@class scale_recorder_visitor : public Base {@\\
\mbox{}\verb@  double factor;@\\
\mbox{}\verb@@\\
\mbox{}\verb@ public:@\\
\mbox{}\verb@@\\
\mbox{}\verb@  scale_recorder_visitor() : factor(1.0) {}@\\
\mbox{}\verb@  scale_recorder_visitor(double x) : factor(x) {}@\\
\mbox{}\verb@@\\
\mbox{}\verb@  double get_factor() const { return factor; }@\\
\mbox{}\verb@  void set_factor(double x) { factor = x; }@\\
\mbox{}\verb@@\\
\mbox{}\verb@#ifdef __BORLANDC__@\\
\mbox{}\verb@#  pragma option push -w-inl@\\
\mbox{}\verb@#endif@\\
\mbox{}\verb@  template <typename ForwardIterator>@\\
\mbox{}\verb@  ForwardIterator transmute(ForwardIterator first, @\\
\mbox{}\verb@                            ForwardIterator last) const {@\\
\mbox{}\verb@    last = Base::transmute(first, last);@\\
\mbox{}\verb@    typedef @\\
\mbox{}\verb@        typename iterator_traits<ForwardIterator>::value_type @\\
\mbox{}\verb@        T;@\\
\mbox{}\verb@    while (first != last) {@\\
\mbox{}\verb@     *first = static_cast<T>(*first * factor);@\\
\mbox{}\verb@     ++first;@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@    return last;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@#ifdef __BORLANDC__@\\
\mbox{}\verb@#  pragma option pop@\\
\mbox{}\verb@#endif@\\
\mbox{}\verb@@\\
\mbox{}\verb@  std::vector<std::string>::iterator @\\
\mbox{}\verb@    transmute(std::vector<std::string>::iterator first, @\\
\mbox{}\verb@              std::vector<std::string>::iterator last) const {@\\
\mbox{}\verb@    return Base::transmute(first, last);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@};@\\
\mbox{}\verb@template <typename Base = default_recorder_visitor>@\\
\mbox{}\verb@class filter_recorder_visitor : public Base {@\\
\mbox{}\verb@  bool filter[NCOUNTERS];@\\
\mbox{}\verb@@\\
\mbox{}\verb@ public:@\\
\mbox{}\verb@  filter_recorder_visitor(bool state = true) { @\\
\mbox{}\verb@    show_all(state); @\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  filter_recorder_visitor(const filter_recorder_visitor& x) @\\
\mbox{}\verb@    : Base(x) {@\\
\mbox{}\verb@    copy(&x.filter[0], @\\
\mbox{}\verb@         &x.filter[sizeof(x.filter) / sizeof(x.filter[0])], @\\
\mbox{}\verb@         &filter[0]);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  filter_recorder_visitor(operator_type op, @\\
\mbox{}\verb@                          bool state = true) {@\\
\mbox{}\verb@    show_all(!state);@\\
\mbox{}\verb@    show(op, state);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  template <typename InputIterator>@\\
\mbox{}\verb@  filter_recorder_visitor(InputIterator first, @\\
\mbox{}\verb@                          InputIterator last, @\\
\mbox{}\verb@                          bool state = true) {@\\
\mbox{}\verb@    show_all(!state);@\\
\mbox{}\verb@    show(first, last, state);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@@\\
\mbox{}\verb@  void show_all(bool state = true) {@\\
\mbox{}\verb@    std::fill(&filter[0], @\\
\mbox{}\verb@         &filter[sizeof(filter) / sizeof(filter[0])], state);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  void hide_all() { show_all(false); }@\\
\mbox{}\verb@  void show(operator_type op, bool state = true) {@\\
\mbox{}\verb@    filter[op] = state;  @\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  void hide(operator_type op) {@\\
\mbox{}\verb@    show(op, false);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@#ifdef __BORLANDC__@\\
\mbox{}\verb@#  pragma option push -w-inl@\\
\mbox{}\verb@#endif@\\
\mbox{}\verb@  template <typename InputIterator>@\\
\mbox{}\verb@  void show(InputIterator first, InputIterator last, @\\
\mbox{}\verb@            bool state = true) {@\\
\mbox{}\verb@    while (first != last)@\\
\mbox{}\verb@      filter[*first++] = state;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@#ifdef __BORLANDC__@\\
\mbox{}\verb@#  pragma option pop@\\
\mbox{}\verb@#endif@\\
\mbox{}\verb@  template <typename InputIterator>@\\
\mbox{}\verb@  void hide(InputIterator first, InputIterator last) {@\\
\mbox{}\verb@    show(first, last, false);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@@\\
\mbox{}\verb@#ifdef __BORLANDC__@\\
\mbox{}\verb@#  pragma option push -w-inl@\\
\mbox{}\verb@#endif@\\
\mbox{}\verb@  template <typename ForwardIterator>@\\
\mbox{}\verb@  ForwardIterator transmute(ForwardIterator first, @\\
\mbox{}\verb@                            ForwardIterator last) const {@\\
\mbox{}\verb@    last = Base::transmute(first, last);@\\
\mbox{}\verb@@\\
\mbox{}\verb@    int i = 0;@\\
\mbox{}\verb@    while (first != last && filter[i++])@\\
\mbox{}\verb@      ++first;@\\
\mbox{}\verb@    if (first == last)@\\
\mbox{}\verb@      return last;@\\
\mbox{}\verb@    ForwardIterator result = first;  @\\
\mbox{}\verb@    for (--i; first != last; ++first)@\\
\mbox{}\verb@      if (filter[i++]) {@\\
\mbox{}\verb@        *result = *first;@\\
\mbox{}\verb@        ++result;@\\
\mbox{}\verb@      }@\\
\mbox{}\verb@    return result;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@#ifdef __BORLANDC__@\\
\mbox{}\verb@#  pragma option pop@\\
\mbox{}\verb@#endif@\\
\mbox{}\verb@};@\\
\mbox{}\verb@template <typename Base = default_recorder_visitor>@\\
\mbox{}\verb@class group_recorder_visitor @\\
\mbox{}\verb@  : public filter_recorder_visitor<Base> {@\\
\mbox{}\verb@@\\
\mbox{}\verb@  std::vector<std::string> names;@\\
\mbox{}\verb@  std::vector<std::vector<operator_type> > groups;@\\
\mbox{}\verb@@\\
\mbox{}\verb@ public:@\\
\mbox{}\verb@  group_recorder_visitor() {}@\\
\mbox{}\verb@  group_recorder_visitor(const std::string& name, @\\
\mbox{}\verb@                     const std::vector<operator_type>& group) {@\\
\mbox{}\verb@    add(name, group); @\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  group_recorder_visitor(const group_recorder_visitor& x) @\\
\mbox{}\verb@    : filter_recorder_visitor<Base>(x), @\\
\mbox{}\verb@      names(x.names), groups(x.groups) {@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  template <typename InputIterator>@\\
\mbox{}\verb@  group_recorder_visitor(const std::string& name, @\\
\mbox{}\verb@                         InputIterator first, @\\
\mbox{}\verb@                         InputIterator last) {@\\
\mbox{}\verb@    add(name, first, last);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@@\\
\mbox{}\verb@  void add(const std::string& name, @\\
\mbox{}\verb@           const std::vector<operator_type>& group) { @\\
\mbox{}\verb@    names.push_back(name);@\\
\mbox{}\verb@    groups.push_back(group); @\\
\mbox{}\verb@    hide(group.begin() + 1, group.end());@\\
\mbox{}\verb@  }  @\\
\mbox{}\verb@@\\
\mbox{}\verb@  template <typename InputIterator>@\\
\mbox{}\verb@  void add(const std::string& name, @\\
\mbox{}\verb@           InputIterator first, InputIterator last) { @\\
\mbox{}\verb@    add(name, std::vector<operator_type>(first, last)); @\\
\mbox{}\verb@  }  @\\
\mbox{}\verb@@\\
\mbox{}\verb@#ifdef __BORLANDC__@\\
\mbox{}\verb@#  pragma option push -w-inl@\\
\mbox{}\verb@#endif@\\
\mbox{}\verb@  template <typename RandomAccessIterator>@\\
\mbox{}\verb@  RandomAccessIterator @\\
\mbox{}\verb@    transmute(RandomAccessIterator first, @\\
\mbox{}\verb@              RandomAccessIterator last) const {@\\
\mbox{}\verb@    for (int i = 0, n = groups.size(); i < n; ++i)@\\
\mbox{}\verb@      for (int j = 1, m = groups[i].size(); j < m; ++j)@\\
\mbox{}\verb@        first[groups[i][0]] += first[groups[i][j]];@\\
\mbox{}\verb@    return filter_recorder_visitor<Base>::transmute(first, @\\
\mbox{}\verb@                                                    last);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@@\\
\mbox{}\verb@  std::vector<std::string>::iterator @\\
\mbox{}\verb@    transmute(std::vector<std::string>::iterator first, @\\
\mbox{}\verb@              std::vector<std::string>::iterator last) const {@\\
\mbox{}\verb@    for (int i = 0, n = groups.size(); i < n; ++i)@\\
\mbox{}\verb@      first[groups[i][0]] = names[i].c_str();@\\
\mbox{}\verb@    return filter_recorder_visitor<Base>::transmute(first, @\\
\mbox{}\verb@                                                    last);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@#ifdef __BORLANDC__@\\
\mbox{}\verb@#  pragma option pop@\\
\mbox{}\verb@#endif@\\
\mbox{}\verb@};@\\
\mbox{}\verb@template <typename Pair>@\\
\mbox{}\verb@struct iter_ref_2nd@\\
\mbox{}\verb@  : public std::unary_function<Pair, @\\
\mbox{}\verb@                          std::pair<typename Pair::first_type, @\\
\mbox{}\verb@      typename std::iterator_traits<typename Pair::second_type>@\\
\mbox{}\verb@                   ::value_type> > {@\\
\mbox{}\verb@  typedef std::pair<typename Pair::first_type, @\\
\mbox{}\verb@      typename std::iterator_traits<typename Pair::second_type>@\\
\mbox{}\verb@                   ::value_type> result_type;@\\
\mbox{}\verb@  result_type operator()(const Pair& x) {@\\
\mbox{}\verb@    return std::make_pair(x.first, *x.second);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@};@\\
\mbox{}\verb@@\\
\mbox{}\verb@template <typename Pair>@\\
\mbox{}\verb@struct myselect2nd :@\\
\mbox{}\verb@  public std::unary_function<Pair, @\\
\mbox{}\verb@                             typename Pair::second_type> {@\\
\mbox{}\verb@  typename Pair::second_type& operator()(Pair& x) const {@\\
\mbox{}\verb@    return x.second;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  const typename Pair::second_type& @\\
\mbox{}\verb@    operator()(const Pair& x) const {@\\
\mbox{}\verb@    return x.second;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@};@\\
\mbox{}\verb@@\\
\mbox{}\verb@template <typename Sequence>@\\
\mbox{}\verb@struct subscript@\\
\mbox{}\verb@  : public std::unary_function<Sequence, @\\
\mbox{}\verb@                          typename Sequence::value_type> {@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  subscript(const typename Sequence::size_type& x = 0) @\\
\mbox{}\verb@    : n(x) {}@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  typename Sequence::reference operator()(Sequence& x) const {@\\
\mbox{}\verb@    return x[n];@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  typename Sequence::const_reference @\\
\mbox{}\verb@    operator()(const Sequence& x) const {@\\
\mbox{}\verb@    return x[n];@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@ protected:@\\
\mbox{}\verb@  typename Sequence::size_type n;@\\
\mbox{}\verb@};@\\
\mbox{}\verb@  @\\
\mbox{}\verb@template <typename Key, typename T, typename Compare, @\\
\mbox{}\verb@          typename Allocator>@\\
\mbox{}\verb@struct subscript<std::map<Key, T, Compare, Allocator> >@\\
\mbox{}\verb@  : public std::unary_function<std::map<Key, T, @\\
\mbox{}\verb@                                        Compare, Allocator>,@\\
\mbox{}\verb@      typename std::map<Key, T, @\\
\mbox{}\verb@                        Compare, Allocator>::mapped_type> {@\\
\mbox{}\verb@@\\
\mbox{}\verb@  subscript() : n() {}@\\
\mbox{}\verb@  subscript(const typename std::map<Key, T, Compare, @\\
\mbox{}\verb@                               Allocator>::key_type& x) @\\
\mbox{}\verb@    : n(x) {}@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  typename std::map<Key, T, @\\
\mbox{}\verb@                    Compare, Allocator>::mapped_type& @\\
\mbox{}\verb@  operator()(std::map<Key, T, @\\
\mbox{}\verb@                      Compare, Allocator>& x) const {@\\
\mbox{}\verb@    return x[n];@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  const typename std::map<Key, T, @\\
\mbox{}\verb@                          Compare, Allocator>::mapped_type& @\\
\mbox{}\verb@  operator()(const std::map<Key, T, @\\
\mbox{}\verb@                            Compare, Allocator>& x) const {@\\
\mbox{}\verb@    return x.find(n)->second;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@ protected:@\\
\mbox{}\verb@  typename std::map<Key, T, Compare, Allocator>::key_type n;@\\
\mbox{}\verb@};@\\
\mbox{}\verb@@\\
\mbox{}\verb@template <typename Counter>@\\
\mbox{}\verb@class recorder;@\\
\mbox{}\verb@template <typename Counter>@\\
\mbox{}\verb@std::ostream& operator<<(std::ostream& out, @\\
\mbox{}\verb@                         const recorder<Counter>&rhs);@\\
\mbox{}\verb@@\\
\mbox{}\verb@template <typename Counter = DEFAULT_COUNTER_TYPE>@\\
\mbox{}\verb@class recorder {@\\
\mbox{}\verb@@\\
\mbox{}\verb@ public:@\\
\mbox{}\verb@ typedef Counter counter_type;@\\
\mbox{}\verb@ typedef std::vector<Counter> counter_vector_type;@\\
\mbox{}\verb@ typedef std::multimap<std::string, @\\
\mbox{}\verb@                       counter_vector_type*> map_type;@\\
\mbox{}\verb@@\\
\mbox{}\verb@ private:@\\
\mbox{}\verb@  map_type counters;@\\
\mbox{}\verb@  typedef std::multimap<std::string, @\\
\mbox{}\verb@                          counter_vector_type> snapshot_type;@\\
\mbox{}\verb@  std::vector<snapshot_type> snapshots;@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  typedef std::map<std::string, counter_vector_type> datum_type;@\\
\mbox{}\verb@  typedef std::vector<datum_type> data_type;@\\
\mbox{}\verb@  data_type data;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  static const char* const counter_tags[NCOUNTERS];@\\
\mbox{}\verb@  static map_type* registry;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  friend std::ostream& operator<< <Counter>(std::ostream& out, @\\
\mbox{}\verb@                              const recorder<Counter>&rhs);@\\
\mbox{}\verb@@\\
\mbox{}\verb@ public:@\\
\mbox{}\verb@  recorder() : counters(*registry), data() {@\\
\mbox{}\verb@    pause();@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  recorder(const map_type& x) : counters(x), data() {@\\
\mbox{}\verb@    pause();@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@@\\
\mbox{}\verb@  void clear() { data.clear(); }@\\
\mbox{}\verb@  void pause();@\\
\mbox{}\verb@  void resume();@\\
\mbox{}\verb@  void record();@\\
\mbox{}\verb@  void reset();@\\
\mbox{}\verb@@\\
\mbox{}\verb@  static counter_vector_type* create(const std::string& x, @\\
\mbox{}\verb@       typename counter_vector_type::size_type n = NCOUNTERS) {@\\
\mbox{}\verb@    if (registry == NULL)@\\
\mbox{}\verb@      registry = new map_type();@\\
\mbox{}\verb@    counter_vector_type* counters = new counter_vector_type(n);@\\
\mbox{}\verb@    registry->insert(make_pair(x, counters));@\\
\mbox{}\verb@    return counters;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@@\\
\mbox{}\verb@  std::ostream& report(std::ostream& out, @\\
\mbox{}\verb@                         const char* delim = "\t") const {@\\
\mbox{}\verb@    return report(out, default_recorder_visitor(), delim);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  template <typename Visitor>@\\
\mbox{}\verb@  std::ostream& report(std::ostream& out, const Visitor& visitor,@\\
\mbox{}\verb@                  const char* delim = "\t") const;@\\
\mbox{}\verb@  std::ostream& report_headings(std::ostream& out,@\\
\mbox{}\verb@                           const char* delim = "\t") const {@\\
\mbox{}\verb@    return report_headings(out, default_recorder_visitor(), @\\
\mbox{}\verb@                           delim);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  template <typename Visitor>@\\
\mbox{}\verb@  std::ostream& report_headings(std::ostream& out, @\\
\mbox{}\verb@                                const Visitor& visitor,@\\
\mbox{}\verb@                           const char* delim = "\t") const;@\\
\mbox{}\verb@  std::ostream& report_table(std::ostream& out,@\\
\mbox{}\verb@                        const char* delim = "\t") const {@\\
\mbox{}\verb@    return report_table(out, default_recorder_visitor(), delim);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  template <typename Visitor>@\\
\mbox{}\verb@  std::ostream& report_table(std::ostream& out, @\\
\mbox{}\verb@                             const Visitor& visitor,@\\
\mbox{}\verb@                        const char* delim = "\t") const;@\\
\mbox{}\verb@  std::ostream& report_totals(std::ostream& out,@\\
\mbox{}\verb@                         const char* delim = "\t") {@\\
\mbox{}\verb@    return report_totals(out, default_recorder_visitor(), delim);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  template <typename Visitor>@\\
\mbox{}\verb@  std::ostream& report_totals(std::ostream& out,@\\
\mbox{}\verb@                         const Visitor& visitor,@\\
\mbox{}\verb@                         const char* delim = "\t");@\\
\mbox{}\verb@@\\
\mbox{}\verb@  typedef typename boost::transform_iterator_generator<@\\
\mbox{}\verb@              subscript<counter_vector_type>, @\\
\mbox{}\verb@              typename boost::projection_iterator_generator<@\\
\mbox{}\verb@                myselect2nd<typename datum_type::value_type>, @\\
\mbox{}\verb@                typename datum_type::iterator>::type>::type @\\
\mbox{}\verb@      column_iterator;@\\
\mbox{}\verb@  typedef typename boost::transform_iterator_generator<@\\
\mbox{}\verb@            subscript<counter_vector_type>, @\\
\mbox{}\verb@            typename boost::projection_iterator_generator<@\\
\mbox{}\verb@              myselect2nd<typename datum_type::value_type>, @\\
\mbox{}\verb@              typename datum_type::const_iterator>::type>::type @\\
\mbox{}\verb@      const_column_iterator;@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  static column_iterator @\\
\mbox{}\verb@    make_column_iterator(typename datum_type::iterator ij, @\\
\mbox{}\verb@                     typename counter_vector_type::size_type k) {@\\
\mbox{}\verb@    return boost::make_transform_iterator(@\\
\mbox{}\verb@        boost::make_projection_iterator(ij, @\\
\mbox{}\verb@                myselect2nd<typename datum_type::value_type>()), @\\
\mbox{}\verb@        subscript<counter_vector_type>(k));@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  static const_column_iterator @\\
\mbox{}\verb@    make_column_iterator(typename datum_type::const_iterator ij, @\\
\mbox{}\verb@                     typename counter_vector_type::size_type k) {@\\
\mbox{}\verb@    return boost::make_transform_iterator(@\\
\mbox{}\verb@        boost::make_projection_iterator(ij, @\\
\mbox{}\verb@                myselect2nd<typename datum_type::value_type>()), @\\
\mbox{}\verb@        subscript<counter_vector_type>(k));@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  typedef typename boost::transform_iterator_generator<@\\
\mbox{}\verb@            subscript<counter_vector_type>, @\\
\mbox{}\verb@            typename boost::transform_iterator_generator<@\\
\mbox{}\verb@              subscript<datum_type>, @\\
\mbox{}\verb@              typename data_type::iterator>::type>::type @\\
\mbox{}\verb@      pole_iterator;@\\
\mbox{}\verb@  typedef typename boost::transform_iterator_generator<@\\
\mbox{}\verb@            subscript<counter_vector_type>, @\\
\mbox{}\verb@            typename boost::transform_iterator_generator<@\\
\mbox{}\verb@              subscript<datum_type>, @\\
\mbox{}\verb@              typename data_type::const_iterator>::type>::type @\\
\mbox{}\verb@      const_pole_iterator;@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  static pole_iterator @\\
\mbox{}\verb@    make_pole_iterator(typename data_type::iterator i, @\\
\mbox{}\verb@                       const typename datum_type::key_type& j, @\\
\mbox{}\verb@                   typename counter_vector_type::size_type k) {@\\
\mbox{}\verb@    return boost::make_transform_iterator(@\\
\mbox{}\verb@        boost::make_transform_iterator(i, @\\
\mbox{}\verb@                        subscript<datum_type>(j)), @\\
\mbox{}\verb@        subscript<counter_vector_type>(k));@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  #ifdef __BORLANDC__@\\
\mbox{}\verb@  #  pragma option push -w-inl@\\
\mbox{}\verb@  #endif@\\
\mbox{}\verb@  static const_pole_iterator @\\
\mbox{}\verb@    make_pole_iterator(typename data_type::const_iterator i, @\\
\mbox{}\verb@                       const typename datum_type::key_type& j, @\\
\mbox{}\verb@                   typename counter_vector_type::size_type k) {@\\
\mbox{}\verb@    return boost::make_transform_iterator(@\\
\mbox{}\verb@        boost::make_transform_iterator(i, @\\
\mbox{}\verb@                        subscript<datum_type>(j)), @\\
\mbox{}\verb@        subscript<counter_vector_type>(k));@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  #ifdef __BORLANDC__@\\
\mbox{}\verb@  #  pragma option pop@\\
\mbox{}\verb@  #endif@\\
\mbox{}\verb@};@\\
\mbox{}\verb@@\\
\mbox{}\verb@template <typename Counter>@\\
\mbox{}\verb@const char* const @\\
\mbox{}\verb@  recorder<Counter>::counter_tags[NCOUNTERS] = {@\\
\mbox{}\verb@  "x()", "x(y)",@\\
\mbox{}\verb@  "x(?)", "base", "~x", "gen",@\\
\mbox{}\verb@  "op=", "cast()", "op<", "op==",@\\
\mbox{}\verb@  "op++", "++op", @\\
\mbox{}\verb@  "op--", "--op",@\\
\mbox{}\verb@  "op+()", "op-()", "op+", "op-", "op*", "op/", "op%",@\\
\mbox{}\verb@  "op<<", "op>>",@\\
\mbox{}\verb@  "op+=", "op-=", "op*=", "op/=", "op%=",@\\
\mbox{}\verb@  "op<<=", "op>>=",@\\
\mbox{}\verb@  "*op", "op->", "op[]", "op()",@\\
\mbox{}\verb@  "op~", "op&", "op&=", "op|", "op|=", "op^", "op^=",@\\
\mbox{}\verb@};@\\
\mbox{}\verb@@\\
\mbox{}\verb@template <typename Counter>@\\
\mbox{}\verb@typename recorder<Counter>::map_type* @\\
\mbox{}\verb@recorder<Counter>::registry;@\\
\mbox{}\verb@@\\
\mbox{}\verb@template <typename Counter>@\\
\mbox{}\verb@void recorder<Counter>::pause() { @\\
\mbox{}\verb@  snapshots.push_back(snapshot_type());@\\
\mbox{}\verb@  snapshot_type& snapshot = snapshots.back();@\\
\mbox{}\verb@  transform(counters.begin(), counters.end(), @\\
\mbox{}\verb@            inserter(snapshot, snapshot.end()),@\\
\mbox{}\verb@            iter_ref_2nd<typename map_type::value_type>());@\\
\mbox{}\verb@}@\\
\mbox{}\verb@template <typename Counter>@\\
\mbox{}\verb@void recorder<Counter>::resume() { @\\
\mbox{}\verb@  // obtain the current counter values@\\
\mbox{}\verb@  snapshot_type current;@\\
\mbox{}\verb@  transform(counters.begin(), counters.end(), @\\
\mbox{}\verb@            inserter(current, current.end()),@\\
\mbox{}\verb@            iter_ref_2nd<typename map_type::value_type>());@\\
\mbox{}\verb@  // get the saved values from the pause action@\\
\mbox{}\verb@  snapshot_type &snapshot = snapshots.back();@\\
\mbox{}\verb@  // baseline += current - snapshot@\\
\mbox{}\verb@  snapshot_type& baseline = snapshots[snapshots.size() - 2];@\\
\mbox{}\verb@  for (typename snapshot_type::iterator i = current.begin(), @\\
\mbox{}\verb@                               j = snapshot.begin(), @\\
\mbox{}\verb@                               k = baseline.begin();@\\
\mbox{}\verb@       i != current.end();@\\
\mbox{}\verb@       ++i, ++j, ++k) {@\\
\mbox{}\verb@    transform(k->second.begin(), k->second.end(), @\\
\mbox{}\verb@              i->second.begin(), k->second.begin(), @\\
\mbox{}\verb@              std::plus<counter_type>());@\\
\mbox{}\verb@    transform(k->second.begin(), k->second.end(), @\\
\mbox{}\verb@              j->second.begin(), k->second.begin(), @\\
\mbox{}\verb@              std::minus<counter_type>());@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  snapshots.pop_back();@\\
\mbox{}\verb@}@\\
\mbox{}\verb@template <typename Counter>@\\
\mbox{}\verb@void recorder<Counter>::record() {@\\
\mbox{}\verb@  data.push_back(datum_type());@\\
\mbox{}\verb@  datum_type& datum = data.back();@\\
\mbox{}\verb@  snapshot_type& baseline = snapshots.back();@\\
\mbox{}\verb@  typename snapshot_type::iterator j = baseline.begin();@\\
\mbox{}\verb@  for (typename map_type::iterator i = counters.begin(); @\\
\mbox{}\verb@       i != counters.end(); @\\
\mbox{}\verb@       ++i, ++j) {@\\
\mbox{}\verb@    counter_vector_type& elt = datum[i->first];@\\
\mbox{}\verb@    if (elt.size() < i->second->size()) {@\\
\mbox{}\verb@      elt.reserve(i->second->size());@\\
\mbox{}\verb@      elt.insert(elt.end(), i->second->size() - elt.size(), 0);@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@    transform(i->second->begin(), i->second->end(), @\\
\mbox{}\verb@              elt.begin(), elt.begin(), @\\
\mbox{}\verb@              std::plus<counter_type>());@\\
\mbox{}\verb@    transform(elt.begin(), elt.end(), @\\
\mbox{}\verb@              j->second.begin(), elt.begin(), @\\
\mbox{}\verb@              std::minus<counter_type>());@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  reset();@\\
\mbox{}\verb@}@\\
\mbox{}\verb@template <typename Counter>@\\
\mbox{}\verb@void recorder<Counter>::reset() {@\\
\mbox{}\verb@  snapshot_type& baseline = snapshots.back();@\\
\mbox{}\verb@  baseline.clear();@\\
\mbox{}\verb@  transform(counters.begin(), counters.end(), @\\
\mbox{}\verb@            inserter(baseline, baseline.end()), @\\
\mbox{}\verb@            iter_ref_2nd<typename map_type::value_type>());@\\
\mbox{}\verb@}@\\
\mbox{}\verb@template <typename Counter>@\\
\mbox{}\verb@template <typename Visitor>@\\
\mbox{}\verb@std::ostream& @\\
\mbox{}\verb@recorder<Counter>::report(std::ostream& out, @\\
\mbox{}\verb@                          const Visitor& visitor,@\\
\mbox{}\verb@                          const char* delim) const {@\\
\mbox{}\verb@  report_headings(out, visitor, delim);@\\
\mbox{}\verb@  report_table(out, visitor, delim);@\\
\mbox{}\verb@  const_cast<recorder<Counter>*>(this)->report_totals(out, @\\
\mbox{}\verb@                                                      visitor, @\\
\mbox{}\verb@                                                      delim);@\\
\mbox{}\verb@  return out;@\\
\mbox{}\verb@}@\\
\mbox{}\verb@template <typename Counter>@\\
\mbox{}\verb@template <typename Visitor>@\\
\mbox{}\verb@std::ostream& @\\
\mbox{}\verb@recorder<Counter>::report_headings(std::ostream& out, @\\
\mbox{}\verb@                                   const Visitor& visitor,@\\
\mbox{}\verb@                                   const char* delim) const {@\\
\mbox{}\verb@  std::vector<std::string> tmp(counter_tags, @\\
\mbox{}\verb@                     counter_tags + @\\
\mbox{}\verb@                       sizeof(counter_tags) / @\\
\mbox{}\verb@                       sizeof(counter_tags[0]));@\\
\mbox{}\verb@  std::vector<std::string>::iterator last = @\\
\mbox{}\verb@          visitor.transmute(tmp.begin(), tmp.end());@\\
\mbox{}\verb@@\\
\mbox{}\verb@  out << std::setw(20) << "Type" << delim;@\\
\mbox{}\verb@  std::copy(tmp.begin(), last, @\\
\mbox{}\verb@       std::ostream_iterator<std::string>(out, delim));@\\
\mbox{}\verb@  return out << "Total" << std::endl;@\\
\mbox{}\verb@}@\\
\mbox{}\verb@template <typename Counter>@\\
\mbox{}\verb@template <typename Visitor>@\\
\mbox{}\verb@std::ostream& @\\
\mbox{}\verb@  recorder<Counter>::report_table(std::ostream& out, @\\
\mbox{}\verb@                                  const Visitor &visitor,@\\
\mbox{}\verb@                                  const char* delim) const {@\\
\mbox{}\verb@  counter_vector_type tmp;@\\
\mbox{}\verb@  for (typename datum_type::const_iterator @\\
\mbox{}\verb@       i = data.front().begin();@\\
\mbox{}\verb@       i != data.front().end();@\\
\mbox{}\verb@       ++i) {@\\
\mbox{}\verb@    tmp.clear();@\\
\mbox{}\verb@    for (size_t j = 0; j < i->second.size(); ++j)@\\
\mbox{}\verb@      tmp.push_back(visitor.choose_element(@\\
\mbox{}\verb@              make_pole_iterator(data.begin(), i->first, j), @\\
\mbox{}\verb@              make_pole_iterator(data.end(), i->first, j)));@\\
\mbox{}\verb@    typename counter_vector_type::iterator last = @\\
\mbox{}\verb@        visitor.transmute(tmp.begin(), tmp.end());@\\
\mbox{}\verb@@\\
\mbox{}\verb@    out << std::setw(20) << i->first.c_str() << delim;@\\
\mbox{}\verb@    std::copy(tmp.begin(), last, @\\
\mbox{}\verb@         std::ostream_iterator<counter_type>(out, delim));@\\
\mbox{}\verb@    out << std::accumulate(tmp.begin(), last, counter_type(0))@\\
\mbox{}\verb@        << std::endl;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  return out;@\\
\mbox{}\verb@}@\\
\mbox{}\verb@template <typename Counter>@\\
\mbox{}\verb@template <typename Visitor>@\\
\mbox{}\verb@std::ostream& @\\
\mbox{}\verb@recorder<Counter>::report_totals(std::ostream& out, @\\
\mbox{}\verb@                                 const Visitor& visitor,@\\
\mbox{}\verb@                                 const char* delim) {@\\
\mbox{}\verb@  counter_vector_type tmp, tmp2;@\\
\mbox{}\verb@  for (size_t op_idx = 0; op_idx < NCOUNTERS; ++op_idx) {@\\
\mbox{}\verb@    tmp.clear();@\\
\mbox{}\verb@    for (size_t j = 0; j < data.size(); ++j)@\\
\mbox{}\verb@      if (op_idx == GENERATION)@\\
\mbox{}\verb@        tmp.push_back(*std::max_element(@\\
\mbox{}\verb@                make_column_iterator(data[j].begin(), op_idx), @\\
\mbox{}\verb@                make_column_iterator(data[j].end(), op_idx)));@\\
\mbox{}\verb@      else@\\
\mbox{}\verb@        tmp.push_back(std::accumulate(@\\
\mbox{}\verb@                make_column_iterator(data[j].begin(), op_idx),@\\
\mbox{}\verb@                make_column_iterator(data[j].end(), op_idx), @\\
\mbox{}\verb@                counter_type(0)));@\\
\mbox{}\verb@@\\
\mbox{}\verb@    // At this point, tmp is a vector of counts of this@\\
\mbox{}\verb@    //  operation.  apply the functor to get a single count @\\
\mbox{}\verb@    // from this set (max, min, etc)@\\
\mbox{}\verb@    tmp2.push_back(visitor.choose_element(tmp.begin(), @\\
\mbox{}\verb@                                          tmp.end()));@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  typename counter_vector_type::iterator last = @\\
\mbox{}\verb@      visitor.transmute(tmp2.begin(), tmp2.end());@\\
\mbox{}\verb@@\\
\mbox{}\verb@  out << std::setw(20) << "Total" << delim;@\\
\mbox{}\verb@  copy(tmp2.begin(), last, @\\
\mbox{}\verb@       std::ostream_iterator<counter_type>(out, delim));@\\
\mbox{}\verb@  return out << std::accumulate(tmp2.begin(), last, @\\
\mbox{}\verb@                                counter_type(0)) @\\
\mbox{}\verb@             << std::endl;@\\
\mbox{}\verb@}@\\
\mbox{}\verb@template <typename Counter>@\\
\mbox{}\verb@std::ostream& operator<< (std::ostream& out, @\\
\mbox{}\verb@                          const recorder<Counter>&rhs) {@\\
\mbox{}\verb@  return rhs.report(out);@\\
\mbox{}\verb@}@\\
\mbox{}\verb@template <typename Difference, typename Counter>@\\
\mbox{}\verb@class difference_counter;@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@template <typename Difference,@\\
\mbox{}\verb@          typename Counter = DEFAULT_COUNTER_TYPE>@\\
\mbox{}\verb@class difference_counter {@\\
\mbox{}\verb@public:@\\
\mbox{}\verb@  typedef Difference difference_type;@\\
\mbox{}\verb@  typedef Counter counter_type;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  difference_counter() : base_difference(), generation(0) {@\\
\mbox{}\verb@    ++counters[DEFAULT_CTOR];@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  difference_counter(const difference_counter& x)@\\
\mbox{}\verb@    : base_difference(x.base_difference), @\\
\mbox{}\verb@      generation(x.generation + 1) {@\\
\mbox{}\verb@    ++counters[COPY_CTOR];@\\
\mbox{}\verb@    counters[GENERATION] = max(counters[GENERATION], generation);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  difference_counter(const difference_type& x) @\\
\mbox{}\verb@    : base_difference(x), generation(0) {@\\
\mbox{}\verb@    ++counters[OTHER_CTOR];@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  ~difference_counter() {@\\
\mbox{}\verb@    ++counters[DTOR]; @\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  difference_counter& operator=(const difference_counter& x) {@\\
\mbox{}\verb@    ++counters[ASSIGNMENT];@\\
\mbox{}\verb@    base_difference = x.base_difference;@\\
\mbox{}\verb@    generation = x.generation;@\\
\mbox{}\verb@    return *this;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  operator difference_type() const {@\\
\mbox{}\verb@    ++counters[CONVERSION];@\\
\mbox{}\verb@    return static_cast<difference_type>(base_difference);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  difference_type& base() {@\\
\mbox{}\verb@    ++counters[BASE];@\\
\mbox{}\verb@    return base_difference;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  const difference_type& base() const {@\\
\mbox{}\verb@    ++counters[BASE];@\\
\mbox{}\verb@    return base_difference;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  difference_counter operator~() const {@\\
\mbox{}\verb@    ++counters[NEGATE];@\\
\mbox{}\verb@    return difference_counter<Difference, @\\
\mbox{}\verb@                              Counter>(~base_difference);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  difference_counter@\\
\mbox{}\verb@    operator&(const difference_counter& n) const {@\\
\mbox{}\verb@    ++counters[AND];@\\
\mbox{}\verb@    return difference_counter<Difference, Counter>(@\\
\mbox{}\verb@        base_difference & n.base_difference);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  difference_counter operator&(const difference_type& n) const {@\\
\mbox{}\verb@    ++counters[AND];@\\
\mbox{}\verb@    return difference_counter<Difference, @\\
\mbox{}\verb@                   Counter>(base_difference & n);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  difference_counter& operator&=(const difference_counter& n) {@\\
\mbox{}\verb@    ++counters[AND_ASSIGN];@\\
\mbox{}\verb@    base_difference &= n.base_difference;@\\
\mbox{}\verb@    return *this;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  difference_counter& operator&=(const difference_type& n) {@\\
\mbox{}\verb@    ++counters[AND_ASSIGN];@\\
\mbox{}\verb@    base_difference &= n;@\\
\mbox{}\verb@    return *this;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  difference_counter @\\
\mbox{}\verb@    operator|(const difference_counter& n) const {@\\
\mbox{}\verb@    ++counters[OR];@\\
\mbox{}\verb@    return difference_counter<Difference, Counter>(@\\
\mbox{}\verb@        base_difference | n.base_difference);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  difference_counter operator|(const difference_type& n) const {@\\
\mbox{}\verb@    ++counters[OR];@\\
\mbox{}\verb@    return difference_counter<Difference, @\\
\mbox{}\verb@                   Counter>(base_difference | n);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  difference_counter& operator|=(const difference_counter& n) {@\\
\mbox{}\verb@    ++counters[OR_ASSIGN];@\\
\mbox{}\verb@    base_difference |= n.base_difference;@\\
\mbox{}\verb@    return *this;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  difference_counter& operator|=(const difference_type& n) {@\\
\mbox{}\verb@    ++counters[OR_ASSIGN];@\\
\mbox{}\verb@    base_difference |= n;@\\
\mbox{}\verb@    return *this;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  difference_counter @\\
\mbox{}\verb@    operator^(const difference_counter& n) const {@\\
\mbox{}\verb@    ++counters[XOR];@\\
\mbox{}\verb@    return difference_counter<Difference, Counter>(@\\
\mbox{}\verb@        base_difference ^ n.base_difference);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  difference_counter operator^(const difference_type& n) const {@\\
\mbox{}\verb@    ++counters[XOR];@\\
\mbox{}\verb@    return difference_counter<Difference, @\\
\mbox{}\verb@                   Counter>(base_difference ^ n);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  difference_counter& operator^=(const difference_counter& n) {@\\
\mbox{}\verb@    ++counters[XOR_ASSIGN];@\\
\mbox{}\verb@    base_difference ^= n.base_difference;@\\
\mbox{}\verb@    return *this;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  difference_counter& operator^=(const difference_type& n) {@\\
\mbox{}\verb@    ++counters[XOR_ASSIGN];@\\
\mbox{}\verb@    base_difference ^= n;@\\
\mbox{}\verb@    return *this;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  difference_counter operator+() const { @\\
\mbox{}\verb@    ++counters[UNARY_PLUS];@\\
\mbox{}\verb@    return difference_counter<Difference, @\\
\mbox{}\verb@                              Counter>(base_difference); @\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  difference_counter operator-() const { @\\
\mbox{}\verb@    ++counters[UNARY_MINUS];@\\
\mbox{}\verb@    return difference_counter<Difference, @\\
\mbox{}\verb@                              Counter>(-base_difference); @\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  difference_counter& operator++() {@\\
\mbox{}\verb@    ++counters[PRE_INCREMENT];@\\
\mbox{}\verb@    ++base_difference;@\\
\mbox{}\verb@    return *this;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  #ifdef __BORLANDC__@\\
\mbox{}\verb@  #  pragma option push -w-inl@\\
\mbox{}\verb@  #endif@\\
\mbox{}\verb@  difference_counter operator++(int) {@\\
\mbox{}\verb@    difference_counter result = *this;@\\
\mbox{}\verb@    ++counters[POST_INCREMENT];@\\
\mbox{}\verb@    base_difference++;@\\
\mbox{}\verb@    return result;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  #ifdef __BORLANDC__@\\
\mbox{}\verb@  #  pragma option pop@\\
\mbox{}\verb@  #endif@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  difference_counter& operator--() {@\\
\mbox{}\verb@    ++counters[PRE_DECREMENT];@\\
\mbox{}\verb@    --base_difference;@\\
\mbox{}\verb@    return *this;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  #ifdef __BORLANDC__@\\
\mbox{}\verb@  #  pragma option push -w-inl@\\
\mbox{}\verb@  #endif@\\
\mbox{}\verb@  difference_counter operator--(int) {@\\
\mbox{}\verb@    difference_counter result(*this);@\\
\mbox{}\verb@    ++counters[POST_DECREMENT];@\\
\mbox{}\verb@    base_difference--;@\\
\mbox{}\verb@    return result;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  #ifdef __BORLANDC__@\\
\mbox{}\verb@  #  pragma option pop@\\
\mbox{}\verb@  #endif@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  difference_counter operator+(const difference_type& x) const {@\\
\mbox{}\verb@    ++counters[PLUS];@\\
\mbox{}\verb@    return difference_counter<Difference, @\\
\mbox{}\verb@            Counter>(base_difference + x);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  difference_counter @\\
\mbox{}\verb@    operator+(const difference_counter& x) const {@\\
\mbox{}\verb@    ++counters[PLUS];@\\
\mbox{}\verb@    return difference_counter<Difference, @\\
\mbox{}\verb@                              Counter>(@\\
\mbox{}\verb@        base_difference + x.base_difference);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  difference_counter& operator+=(const difference_type& x) {@\\
\mbox{}\verb@    ++counters[PLUS_ASSIGN];@\\
\mbox{}\verb@    base_difference += x;@\\
\mbox{}\verb@    return *this;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  difference_counter& operator+=(const difference_counter& x) {@\\
\mbox{}\verb@    ++counters[PLUS_ASSIGN];@\\
\mbox{}\verb@    base_difference += x.base_difference;@\\
\mbox{}\verb@    return *this;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  difference_counter operator-(const difference_type& x) const {@\\
\mbox{}\verb@    ++counters[MINUS];@\\
\mbox{}\verb@    return difference_counter<Difference, @\\
\mbox{}\verb@                   Counter>(base_difference - x);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  difference_counter @\\
\mbox{}\verb@    operator-(const difference_counter& x) const {@\\
\mbox{}\verb@    ++counters[MINUS];@\\
\mbox{}\verb@    return difference_counter<Difference, Counter>(@\\
\mbox{}\verb@        base_difference - x.base_difference);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  difference_counter& operator-=(const difference_type& x) {@\\
\mbox{}\verb@    ++counters[MINUS_ASSIGN];@\\
\mbox{}\verb@    base_difference -= x;@\\
\mbox{}\verb@    return *this;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  difference_counter& operator-=(const difference_counter& x) {@\\
\mbox{}\verb@    ++counters[MINUS_ASSIGN];@\\
\mbox{}\verb@    base_difference -= x.base_difference;@\\
\mbox{}\verb@    return *this;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  difference_counter operator*(const difference_type& x) const {@\\
\mbox{}\verb@    ++counters[TIMES];@\\
\mbox{}\verb@    return difference_counter<Difference, @\\
\mbox{}\verb@                   Counter>(base_difference * x);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  difference_counter@\\
\mbox{}\verb@    operator*(const difference_counter& x) const {@\\
\mbox{}\verb@    ++counters[TIMES];@\\
\mbox{}\verb@    return difference_counter<Difference, Counter>(@\\
\mbox{}\verb@        base_difference * x.base_difference);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  difference_counter& operator*=(const difference_type& x) {@\\
\mbox{}\verb@    ++counters[TIMES_ASSIGN];@\\
\mbox{}\verb@    base_difference *= x;@\\
\mbox{}\verb@    return *this;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  difference_counter& operator*=(const difference_counter& x) {@\\
\mbox{}\verb@    ++counters[TIMES_ASSIGN];@\\
\mbox{}\verb@    base_difference *= x.base_difference;@\\
\mbox{}\verb@    return *this;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  difference_counter operator/(const difference_type& x) const {@\\
\mbox{}\verb@    ++counters[DIVIDE];@\\
\mbox{}\verb@    return difference_counter<Difference, @\\
\mbox{}\verb@                   Counter>(base_difference / x);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  difference_counter @\\
\mbox{}\verb@    operator/(const difference_counter& x) const {@\\
\mbox{}\verb@    ++counters[DIVIDE];@\\
\mbox{}\verb@    return difference_counter<Difference, Counter>(@\\
\mbox{}\verb@        base_difference / x.base_difference);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  difference_counter& operator/=(const difference_type& x) {@\\
\mbox{}\verb@    ++counters[DIVIDE_ASSIGN];@\\
\mbox{}\verb@    base_difference /= x;@\\
\mbox{}\verb@    return *this;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  difference_counter& operator/=(const difference_counter& x) {@\\
\mbox{}\verb@    ++counters[DIVIDE_ASSIGN];@\\
\mbox{}\verb@    base_difference /= x.base_difference;@\\
\mbox{}\verb@    return *this;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  difference_counter@\\
\mbox{}\verb@    operator%(const difference_counter& x) const {@\\
\mbox{}\verb@    ++counters[MODULO];@\\
\mbox{}\verb@    return difference_counter<Difference, Counter>(@\\
\mbox{}\verb@        base_difference % x.base_difference);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  difference_counter operator%(const difference_type& x) const {@\\
\mbox{}\verb@    ++counters[MODULO];@\\
\mbox{}\verb@    return difference_counter<Difference, @\\
\mbox{}\verb@                   Counter>(base_difference % x);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  difference_counter& operator%=(const difference_counter& x) {@\\
\mbox{}\verb@    ++counters[MODULO_ASSIGN];@\\
\mbox{}\verb@    base_difference %= x.base_difference;@\\
\mbox{}\verb@    return *this;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  difference_counter& operator%=(const difference_type& x) {@\\
\mbox{}\verb@    ++counters[MODULO_ASSIGN];@\\
\mbox{}\verb@    base_difference %= x;@\\
\mbox{}\verb@    return *this;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  difference_counter operator<<(int n) const {@\\
\mbox{}\verb@    ++counters[LEFT_SHIFT];@\\
\mbox{}\verb@    return difference_counter<Difference, @\\
\mbox{}\verb@                   Counter>(base_difference << n);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  difference_counter& operator<<=(int n) {@\\
\mbox{}\verb@    ++counters[LEFT_SHIFT_ASSIGN];@\\
\mbox{}\verb@    base_difference <<= n;@\\
\mbox{}\verb@    return *this;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  difference_counter operator>>(int n) const {@\\
\mbox{}\verb@    ++counters[RIGHT_SHIFT];@\\
\mbox{}\verb@    return difference_counter<Difference, @\\
\mbox{}\verb@                   Counter>(base_difference >> n);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  difference_counter& operator>>=(int n) {@\\
\mbox{}\verb@    ++counters[RIGHT_SHIFT_ASSIGN];@\\
\mbox{}\verb@    base_difference >>= n;@\\
\mbox{}\verb@    return *this;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@@\\
\mbox{}\verb@  friend bool operator==(const difference_counter& lhs,@\\
\mbox{}\verb@                         const difference_counter& rhs) {@\\
\mbox{}\verb@    ++difference_counter::counters[EQUALITY];@\\
\mbox{}\verb@    return lhs.base_difference == rhs.base_difference;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  friend bool operator==(const difference_counter& lhs, @\\
\mbox{}\verb@                         const difference_type& rhs) {@\\
\mbox{}\verb@    ++difference_counter::counters[EQUALITY];@\\
\mbox{}\verb@    return lhs.base_difference == rhs;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  friend bool operator==(const difference_type& lhs, @\\
\mbox{}\verb@                         const difference_counter& rhs) {@\\
\mbox{}\verb@    ++difference_counter::counters[EQUALITY];@\\
\mbox{}\verb@    return lhs == rhs.base_difference;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  friend bool operator!=(const difference_counter& lhs,@\\
\mbox{}\verb@                         const difference_counter& rhs) {@\\
\mbox{}\verb@    ++difference_counter::counters[EQUALITY];@\\
\mbox{}\verb@    return !(lhs.base_difference == rhs.base_difference);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  friend bool operator!=(const difference_counter& lhs, @\\
\mbox{}\verb@                         const difference_type& rhs) {@\\
\mbox{}\verb@    return !(lhs.base_difference == rhs);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  friend bool operator!=(const difference_type& lhs, @\\
\mbox{}\verb@                         const difference_counter& rhs) {@\\
\mbox{}\verb@    return !(lhs == rhs.base_difference);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  friend bool operator<(const difference_counter& lhs, @\\
\mbox{}\verb@                        const difference_counter& rhs) {@\\
\mbox{}\verb@    ++difference_counter::counters[LESS_THAN];@\\
\mbox{}\verb@    return lhs.base_difference < rhs.base_difference;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  friend bool operator<(const difference_counter& lhs, @\\
\mbox{}\verb@                        const difference_type& rhs) {@\\
\mbox{}\verb@    ++difference_counter::counters[LESS_THAN];@\\
\mbox{}\verb@    return lhs.base_difference < rhs;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  friend bool operator<(const difference_type& lhs, @\\
\mbox{}\verb@                        const difference_counter& rhs) {@\\
\mbox{}\verb@    ++difference_counter::counters[LESS_THAN];@\\
\mbox{}\verb@    return lhs < rhs.base_difference;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  friend bool operator>(const difference_counter& lhs, @\\
\mbox{}\verb@                        const difference_counter& rhs) {@\\
\mbox{}\verb@    ++difference_counter::counters[LESS_THAN];@\\
\mbox{}\verb@    return rhs.base_difference < lhs.base_difference;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  friend bool operator>(const difference_counter& lhs, @\\
\mbox{}\verb@                        const difference_type& rhs) {@\\
\mbox{}\verb@    return rhs < lhs.base_difference;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  friend bool operator>(const difference_type& lhs, @\\
\mbox{}\verb@                        const difference_counter& rhs) {@\\
\mbox{}\verb@    return rhs.base_difference < lhs;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  friend bool operator<=(const difference_counter& lhs, @\\
\mbox{}\verb@                         const difference_counter& rhs) {@\\
\mbox{}\verb@    ++difference_counter::counters[LESS_THAN];@\\
\mbox{}\verb@    return !(rhs.base_difference < lhs.base_difference);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  friend bool operator<=(const difference_counter& lhs, @\\
\mbox{}\verb@                        const difference_type& rhs) {@\\
\mbox{}\verb@    return !(rhs < lhs.base_difference);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  friend bool operator<=(const difference_type& lhs, @\\
\mbox{}\verb@                        const difference_counter& rhs) {@\\
\mbox{}\verb@    return !(rhs.base_difference < lhs);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  friend bool operator>=(const difference_counter& lhs, @\\
\mbox{}\verb@                         const difference_counter& rhs) {@\\
\mbox{}\verb@    ++difference_counter::counters[LESS_THAN];@\\
\mbox{}\verb@    return !(lhs.base_difference < rhs.base_difference);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  friend bool operator>=(const difference_counter& lhs, @\\
\mbox{}\verb@                        const difference_type& rhs) {@\\
\mbox{}\verb@    return !(lhs.base_difference < rhs);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  friend bool operator>=(const difference_type& lhs, @\\
\mbox{}\verb@                        const difference_counter& rhs) {@\\
\mbox{}\verb@    return !(lhs < rhs.base_difference);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  template <typename T>@\\
\mbox{}\verb@    friend T* operator+(T* p, const difference_counter& n) { @\\
\mbox{}\verb@      ++counters[PLUS];@\\
\mbox{}\verb@      return p + n.base_difference; @\\
\mbox{}\verb@    }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  template <typename T>@\\
\mbox{}\verb@    friend const T* operator+(const T* p, @\\
\mbox{}\verb@                              const difference_counter& n) { @\\
\mbox{}\verb@      ++counters[PLUS];@\\
\mbox{}\verb@      return p + n.base_difference; @\\
\mbox{}\verb@    }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  template <typename T>@\\
\mbox{}\verb@    friend T*& operator+=(T*& p, const difference_counter& n) { @\\
\mbox{}\verb@      ++counters[PLUS];@\\
\mbox{}\verb@      return p += n.base_difference; @\\
\mbox{}\verb@    }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  template <typename T>@\\
\mbox{}\verb@    friend T* operator-(T* p, const difference_counter& n) { @\\
\mbox{}\verb@      ++counters[MINUS];@\\
\mbox{}\verb@      return p - n.base_difference; @\\
\mbox{}\verb@    }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  template <typename T>@\\
\mbox{}\verb@    friend const T* operator-(const T* p, @\\
\mbox{}\verb@                              const difference_counter& n) { @\\
\mbox{}\verb@      ++counters[MINUS];@\\
\mbox{}\verb@      return p - n.base_difference; @\\
\mbox{}\verb@    }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  template <typename T>@\\
\mbox{}\verb@    friend T*& operator-=(T*& p, const difference_counter& n) { @\\
\mbox{}\verb@      ++counters[MINUS];@\\
\mbox{}\verb@      return p -= n.base_difference; @\\
\mbox{}\verb@    }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  friend difference_counter @\\
\mbox{}\verb@    operator&(const difference_type& lhs,@\\
\mbox{}\verb@              const difference_counter& rhs) {@\\
\mbox{}\verb@    ++counters[AND];@\\
\mbox{}\verb@    return difference_counter<Difference, Counter>(@\\
\mbox{}\verb@        lhs & rhs.base_difference);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  friend difference_type& @\\
\mbox{}\verb@    operator&=(const difference_type& lhs,@\\
\mbox{}\verb@               const difference_counter& rhs) {@\\
\mbox{}\verb@    ++counters[AND];@\\
\mbox{}\verb@    return lhs &= rhs.base_difference;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  friend difference_counter @\\
\mbox{}\verb@    operator|(const difference_type& lhs,@\\
\mbox{}\verb@              const difference_counter& rhs) {@\\
\mbox{}\verb@    ++counters[OR];@\\
\mbox{}\verb@    return difference_counter<Difference, Counter>(@\\
\mbox{}\verb@        lhs | rhs.base_difference);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  friend difference_type& @\\
\mbox{}\verb@    operator|=(const difference_type& lhs,@\\
\mbox{}\verb@               const difference_counter& rhs) {@\\
\mbox{}\verb@    ++counters[OR];@\\
\mbox{}\verb@    return lhs |= rhs.base_difference;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  friend difference_counter @\\
\mbox{}\verb@    operator^(const difference_type& lhs,@\\
\mbox{}\verb@              const difference_counter& rhs) {@\\
\mbox{}\verb@    ++counters[XOR];@\\
\mbox{}\verb@    return difference_counter<Difference, Counter>(@\\
\mbox{}\verb@        lhs ^ rhs.base_difference);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  friend difference_type& @\\
\mbox{}\verb@    operator^=(const difference_type& lhs,@\\
\mbox{}\verb@               const difference_counter& rhs) {@\\
\mbox{}\verb@    ++counters[XOR];@\\
\mbox{}\verb@    return lhs ^= rhs.base_difference;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  friend difference_counter@\\
\mbox{}\verb@    operator+(const difference_type& lhs,@\\
\mbox{}\verb@              const difference_counter& rhs) {@\\
\mbox{}\verb@    ++difference_counter::counters[PLUS];@\\
\mbox{}\verb@    return difference_counter<Difference, Counter>(@\\
\mbox{}\verb@        lhs + rhs.base_difference);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  friend difference_type& @\\
\mbox{}\verb@    operator+=(difference_type& lhs,@\\
\mbox{}\verb@               const difference_counter& rhs) {@\\
\mbox{}\verb@    ++counters[PLUS];@\\
\mbox{}\verb@    lhs += rhs.base_difference;@\\
\mbox{}\verb@    return lhs;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  friend difference_counter @\\
\mbox{}\verb@    operator-(const difference_type& lhs,@\\
\mbox{}\verb@              const difference_counter& rhs) {@\\
\mbox{}\verb@    ++counters[MINUS];@\\
\mbox{}\verb@    return difference_counter<Difference, Counter>(@\\
\mbox{}\verb@        lhs - rhs.base_difference);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  friend difference_type& @\\
\mbox{}\verb@    operator-=(difference_type& lhs,@\\
\mbox{}\verb@               const difference_counter& rhs) {@\\
\mbox{}\verb@    ++counters[MINUS];@\\
\mbox{}\verb@    lhs -= rhs.base_difference;@\\
\mbox{}\verb@    return lhs;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  friend difference_counter @\\
\mbox{}\verb@    operator*(const difference_type& lhs,@\\
\mbox{}\verb@              const difference_counter& rhs) {@\\
\mbox{}\verb@    ++counters[TIMES];@\\
\mbox{}\verb@    return difference_counter<Difference, Counter>(@\\
\mbox{}\verb@        lhs * rhs.base_difference);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  friend difference_type& @\\
\mbox{}\verb@    operator*=(difference_type& lhs,@\\
\mbox{}\verb@               const difference_counter& rhs) {@\\
\mbox{}\verb@    ++counters[TIMES];@\\
\mbox{}\verb@    lhs *= rhs.base_difference;@\\
\mbox{}\verb@    return lhs;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  friend difference_counter @\\
\mbox{}\verb@    operator/(const difference_type& lhs,@\\
\mbox{}\verb@              const difference_counter& rhs) {@\\
\mbox{}\verb@    ++counters[DIVIDE];@\\
\mbox{}\verb@    return difference_counter<Difference, Counter>(@\\
\mbox{}\verb@        lhs / rhs.base_difference);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  friend difference_type& @\\
\mbox{}\verb@    operator/=(difference_type& lhs,@\\
\mbox{}\verb@               const difference_counter& rhs) {@\\
\mbox{}\verb@    ++counters[DIVIDE];@\\
\mbox{}\verb@    lhs /= rhs.base_difference;@\\
\mbox{}\verb@    return lhs;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  friend difference_counter @\\
\mbox{}\verb@    operator%(const difference_type& lhs, @\\
\mbox{}\verb@              const difference_counter& rhs) {@\\
\mbox{}\verb@    ++counters[MODULO];@\\
\mbox{}\verb@    return difference_counter<Difference, Counter>(@\\
\mbox{}\verb@        lhs % rhs.base_difference);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  friend difference_type& @\\
\mbox{}\verb@    operator%=(difference_type& lhs, @\\
\mbox{}\verb@               const difference_counter& rhs) {@\\
\mbox{}\verb@    ++counters[MODULO];@\\
\mbox{}\verb@    lhs %= rhs.base_difference;@\\
\mbox{}\verb@    return lhs;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@@\\
\mbox{}\verb@ protected:@\\
\mbox{}\verb@  difference_type base_difference;@\\
\mbox{}\verb@  Counter generation;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  static typename recorder<Counter>::counter_vector_type& @\\
\mbox{}\verb@         counters;@\\
\mbox{}\verb@};@\\
\mbox{}\verb@@\\
\mbox{}\verb@template <typename Difference, @\\
\mbox{}\verb@          typename Counter>@\\
\mbox{}\verb@  typename recorder<Counter>::counter_vector_type&@\\
\mbox{}\verb@    difference_counter<Difference, Counter>::counters =@\\
\mbox{}\verb@      *recorder<Counter>::create("difference_counter");@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@template <typename Iterator, typename Difference,@\\
\mbox{}\verb@          typename Counter>@\\
\mbox{}\verb@class iterator_counter;@\\
\mbox{}\verb@template <typename Iterator, typename Difference, @\\
\mbox{}\verb@          typename Counter>@\\
\mbox{}\verb@bool operator==(@\\
\mbox{}\verb@    const iterator_counter<Iterator, Difference, @\\
\mbox{}\verb@                           Counter>& lhs, @\\
\mbox{}\verb@    const iterator_counter<Iterator, Difference, @\\
\mbox{}\verb@                           Counter>& rhs);@\\
\mbox{}\verb@template <typename Iterator, typename Difference, @\\
\mbox{}\verb@          typename Counter>@\\
\mbox{}\verb@bool operator!=(@\\
\mbox{}\verb@    const iterator_counter<Iterator, Difference, @\\
\mbox{}\verb@                           Counter>& lhs, @\\
\mbox{}\verb@    const iterator_counter<Iterator, Difference, @\\
\mbox{}\verb@                           Counter>& rhs);@\\
\mbox{}\verb@template <typename Iterator, typename Difference, @\\
\mbox{}\verb@          typename Counter>@\\
\mbox{}\verb@bool operator<(@\\
\mbox{}\verb@    const iterator_counter<Iterator, Difference, @\\
\mbox{}\verb@                           Counter>& lhs,@\\
\mbox{}\verb@    const iterator_counter<Iterator, Difference,@\\
\mbox{}\verb@                           Counter>& rhs);@\\
\mbox{}\verb@template <typename Iterator, typename Difference, @\\
\mbox{}\verb@          typename Counter>@\\
\mbox{}\verb@bool operator>(@\\
\mbox{}\verb@    const iterator_counter<Iterator, Difference, @\\
\mbox{}\verb@                           Counter>& lhs,@\\
\mbox{}\verb@    const iterator_counter<Iterator, Difference, @\\
\mbox{}\verb@                           Counter>& rhs);@\\
\mbox{}\verb@template <typename Iterator, typename Difference, @\\
\mbox{}\verb@          typename Counter>@\\
\mbox{}\verb@bool operator<=(@\\
\mbox{}\verb@    const iterator_counter<Iterator, Difference, @\\
\mbox{}\verb@                           Counter>& lhs,@\\
\mbox{}\verb@    const iterator_counter<Iterator, Difference, @\\
\mbox{}\verb@                           Counter>& rhs);@\\
\mbox{}\verb@template <typename Iterator, typename Difference, @\\
\mbox{}\verb@          typename Counter>@\\
\mbox{}\verb@bool operator>=(@\\
\mbox{}\verb@    const iterator_counter<Iterator, Difference, @\\
\mbox{}\verb@                           Counter>& lhs,@\\
\mbox{}\verb@    const iterator_counter<Iterator, Difference, @\\
\mbox{}\verb@                           Counter>& rhs);@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@template <typename Iterator,@\\
\mbox{}\verb@          typename Difference =@\\
\mbox{}\verb@            difference_counter<typename @\\
\mbox{}\verb@              std::iterator_traits<Iterator>::difference_type>,@\\
\mbox{}\verb@          typename Counter = DEFAULT_COUNTER_TYPE>@\\
\mbox{}\verb@class iterator_counter@\\
\mbox{}\verb@#if defined(_RWSTD_VER) && (_RWSTD_VER <= 0x020101)@\\
\mbox{}\verb@  : public std::iterator<@\\
\mbox{}\verb@      typename std::iterator_traits<Iterator>::@\\
\mbox{}\verb@              iterator_category, @\\
\mbox{}\verb@      typename std::iterator_traits<Iterator>::value_type,  @\\
\mbox{}\verb@      typename std::iterator_traits<Iterator>::difference_type,@\\
\mbox{}\verb@      typename std::iterator_traits<Iterator>::pointer,@\\
\mbox{}\verb@      typename std::iterator_traits<Iterator>::reference> @\\
\mbox{}\verb@#endif@\\
\mbox{}\verb@{@\\
\mbox{}\verb@ public:@\\
\mbox{}\verb@  typedef Iterator iterator_type;@\\
\mbox{}\verb@  typedef Difference difference_type;@\\
\mbox{}\verb@  typedef Counter counter_type;@\\
\mbox{}\verb@  typedef typename std::iterator_traits<Iterator>::value_type@\\
\mbox{}\verb@      value_type;@\\
\mbox{}\verb@  typedef typename std::iterator_traits<Iterator>::pointer @\\
\mbox{}\verb@      pointer;@\\
\mbox{}\verb@  typedef typename std::iterator_traits<Iterator>::reference @\\
\mbox{}\verb@      reference;@\\
\mbox{}\verb@  typedef typename @\\
\mbox{}\verb@      std::iterator_traits<Iterator>::iterator_category@\\
\mbox{}\verb@      iterator_category;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  iterator_counter() : base_iterator(), generation(0) {@\\
\mbox{}\verb@    ++counters[DEFAULT_CTOR];@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  iterator_counter(const iterator_counter& x)@\\
\mbox{}\verb@    : base_iterator(x.base_iterator), @\\
\mbox{}\verb@      generation(x.generation + 1) {@\\
\mbox{}\verb@    ++counters[COPY_CTOR];@\\
\mbox{}\verb@    counters[GENERATION] = max(counters[GENERATION], generation);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  iterator_counter(const iterator_type& x) @\\
\mbox{}\verb@    : base_iterator(x), generation(0) {@\\
\mbox{}\verb@    ++counters[OTHER_CTOR];@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  ~iterator_counter() {@\\
\mbox{}\verb@    ++counters[DTOR]; @\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  iterator_counter& operator=(const iterator_counter& x) {@\\
\mbox{}\verb@    ++counters[ASSIGNMENT];@\\
\mbox{}\verb@    base_iterator = x.base_iterator;@\\
\mbox{}\verb@    generation = x.generation;@\\
\mbox{}\verb@    return *this;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  iterator_type& base() {@\\
\mbox{}\verb@    ++counters[BASE];@\\
\mbox{}\verb@    return base_iterator;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  const iterator_type& base() const {@\\
\mbox{}\verb@    ++counters[BASE];@\\
\mbox{}\verb@    return base_iterator;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  reference operator*() const {@\\
\mbox{}\verb@    ++counters[DEREFERENCE];@\\
\mbox{}\verb@    return *base_iterator;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  pointer operator->() const {@\\
\mbox{}\verb@    ++counters[MEMBER];@\\
\mbox{}\verb@    return &(*base_iterator);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  iterator_counter& operator++() {@\\
\mbox{}\verb@    ++counters[PRE_INCREMENT];@\\
\mbox{}\verb@    ++base_iterator;@\\
\mbox{}\verb@    return *this;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  #ifdef __BORLANDC__@\\
\mbox{}\verb@  #  pragma option push -w-inl@\\
\mbox{}\verb@  #endif@\\
\mbox{}\verb@  iterator_counter operator++(int) {@\\
\mbox{}\verb@    iterator_counter result(*this);@\\
\mbox{}\verb@    ++counters[POST_INCREMENT];@\\
\mbox{}\verb@    base_iterator++;@\\
\mbox{}\verb@    return result;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  #ifdef __BORLANDC__@\\
\mbox{}\verb@  #  pragma option pop@\\
\mbox{}\verb@  #endif@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  iterator_counter& operator--() {@\\
\mbox{}\verb@    ++counters[PRE_DECREMENT];@\\
\mbox{}\verb@    --base_iterator;@\\
\mbox{}\verb@    return *this;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  #ifdef __BORLANDC__@\\
\mbox{}\verb@  #  pragma option push -w-inl@\\
\mbox{}\verb@  #endif@\\
\mbox{}\verb@  iterator_counter operator--(int) {@\\
\mbox{}\verb@    iterator_counter result(*this);@\\
\mbox{}\verb@    ++counters[POST_DECREMENT];@\\
\mbox{}\verb@    base_iterator--;@\\
\mbox{}\verb@    return result;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  #ifdef __BORLANDC__@\\
\mbox{}\verb@  #  pragma option pop@\\
\mbox{}\verb@  #endif@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  iterator_counter operator+(const difference_type& n) const {@\\
\mbox{}\verb@    ++counters[PLUS];@\\
\mbox{}\verb@    return iterator_counter<Iterator, Difference, Counter>(@\\
\mbox{}\verb@        base_iterator + unadapted_difference_type(n));@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  iterator_counter& operator+=(const difference_type& n) {@\\
\mbox{}\verb@    ++counters[PLUS_ASSIGN];@\\
\mbox{}\verb@    base_iterator += unadapted_difference_type(n);@\\
\mbox{}\verb@    return *this;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  iterator_counter operator-(const difference_type& n) const {@\\
\mbox{}\verb@    ++counters[MINUS];@\\
\mbox{}\verb@    return iterator_counter<Iterator, Difference, Counter>(@\\
\mbox{}\verb@        base_iterator - unadapted_difference_type(n));@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  difference_type operator-(const iterator_counter& i) const {@\\
\mbox{}\verb@    ++counters[MINUS];@\\
\mbox{}\verb@    return difference_type(base_iterator - i.base_iterator);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  iterator_counter& operator-=(const difference_type& n) {@\\
\mbox{}\verb@    ++counters[MINUS_ASSIGN];@\\
\mbox{}\verb@    base_iterator -= unadapted_difference_type(n);@\\
\mbox{}\verb@    return *this;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  reference operator[](const difference_type& n) const {@\\
\mbox{}\verb@    ++counters[SUBSCRIPT];@\\
\mbox{}\verb@    return base_iterator[unadapted_difference_type(n)];@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@@\\
\mbox{}\verb@  friend bool operator== <Iterator, Difference, Counter>(@\\
\mbox{}\verb@      const iterator_counter& lhs, @\\
\mbox{}\verb@      const iterator_counter& rhs);@\\
\mbox{}\verb@  friend bool operator!= <Iterator, Difference, Counter>(@\\
\mbox{}\verb@      const iterator_counter& lhs, @\\
\mbox{}\verb@      const iterator_counter& rhs);@\\
\mbox{}\verb@  friend bool operator< <Iterator, Difference, Counter>(@\\
\mbox{}\verb@      const iterator_counter& lhs,@\\
\mbox{}\verb@      const iterator_counter& rhs);@\\
\mbox{}\verb@  friend bool operator> <Iterator, Difference, Counter>(@\\
\mbox{}\verb@      const iterator_counter& lhs,@\\
\mbox{}\verb@      const iterator_counter& rhs);@\\
\mbox{}\verb@  friend bool operator<= <Iterator, Difference, Counter>(@\\
\mbox{}\verb@      const iterator_counter& lhs,@\\
\mbox{}\verb@      const iterator_counter& rhs);@\\
\mbox{}\verb@  friend bool operator>= <Iterator, Difference, Counter>(@\\
\mbox{}\verb@      const iterator_counter& lhs,@\\
\mbox{}\verb@      const iterator_counter& rhs);@\\
\mbox{}\verb@  friend iterator_counter operator+(@\\
\mbox{}\verb@      const difference_type& n,@\\
\mbox{}\verb@      const iterator_counter& i) {@\\
\mbox{}\verb@    ++iterator_counter::counters[PLUS];@\\
\mbox{}\verb@    return iterator_counter<Iterator, Difference, Counter>(@\\
\mbox{}\verb@        i.base_iterator + unadapted_difference_type(n));@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@@\\
\mbox{}\verb@ protected:@\\
\mbox{}\verb@  iterator_type base_iterator;@\\
\mbox{}\verb@  Counter generation;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  static typename recorder<Counter>::counter_vector_type& @\\
\mbox{}\verb@         counters;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  template <typename T>@\\
\mbox{}\verb@    static const @\\
\mbox{}\verb@      typename std::iterator_traits<Iterator>::difference_type& @\\
\mbox{}\verb@        unadapted_difference_type(const T& n) {@\\
\mbox{}\verb@    return n;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  template <typename xDifference, typename xCounter>@\\
\mbox{}\verb@    static const @\\
\mbox{}\verb@      typename std::iterator_traits<Iterator>::difference_type&@\\
\mbox{}\verb@        unadapted_difference_type(@\\
\mbox{}\verb@          const difference_counter<xDifference, @\\
\mbox{}\verb@                                   xCounter>& n) {@\\
\mbox{}\verb@    return n.base();@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@};@\\
\mbox{}\verb@@\\
\mbox{}\verb@template <typename Iterator, typename Difference, @\\
\mbox{}\verb@          typename Counter>@\\
\mbox{}\verb@  typename recorder<Counter>::counter_vector_type&@\\
\mbox{}\verb@    iterator_counter<Iterator, Difference, @\\
\mbox{}\verb@                     Counter>::counters =@\\
\mbox{}\verb@      *recorder<Counter>::create("iterator_counter");@\\
\mbox{}\verb@@\\
\mbox{}\verb@template <typename Iterator, typename Difference, @\\
\mbox{}\verb@          typename Counter>@\\
\mbox{}\verb@bool operator==(@\\
\mbox{}\verb@    const iterator_counter<Iterator, Difference, @\\
\mbox{}\verb@                           Counter>& lhs, @\\
\mbox{}\verb@    const iterator_counter<Iterator, Difference, @\\
\mbox{}\verb@                           Counter>& rhs) {@\\
\mbox{}\verb@  ++iterator_counter<Iterator, Difference, @\\
\mbox{}\verb@                     Counter>::counters[EQUALITY];@\\
\mbox{}\verb@  return lhs.base_iterator == rhs.base_iterator;@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@\\
\mbox{}\verb@template <typename Iterator, typename Difference, @\\
\mbox{}\verb@          typename Counter>@\\
\mbox{}\verb@bool operator!=(@\\
\mbox{}\verb@    const iterator_counter<Iterator, Difference, @\\
\mbox{}\verb@                           Counter>& lhs, @\\
\mbox{}\verb@    const iterator_counter<Iterator, Difference, @\\
\mbox{}\verb@                           Counter>& rhs) {@\\
\mbox{}\verb@  ++iterator_counter<Iterator, Difference, @\\
\mbox{}\verb@                     Counter>::counters[EQUALITY];@\\
\mbox{}\verb@  return !(lhs.base_iterator == rhs.base_iterator);@\\
\mbox{}\verb@}@\\
\mbox{}\verb@template <typename Iterator, typename Difference, @\\
\mbox{}\verb@          typename Counter>@\\
\mbox{}\verb@bool operator<(@\\
\mbox{}\verb@    const iterator_counter<Iterator, Difference, @\\
\mbox{}\verb@                           Counter>& lhs,@\\
\mbox{}\verb@    const iterator_counter<Iterator, Difference, @\\
\mbox{}\verb@                           Counter>& rhs) {@\\
\mbox{}\verb@  ++iterator_counter<Iterator, Difference, @\\
\mbox{}\verb@                     Counter>::counters[LESS_THAN];@\\
\mbox{}\verb@  return lhs.base_iterator < rhs.base_iterator;@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@\\
\mbox{}\verb@template <typename Iterator, typename Difference, @\\
\mbox{}\verb@          typename Counter>@\\
\mbox{}\verb@bool operator>(@\\
\mbox{}\verb@    const iterator_counter<Iterator, Difference, @\\
\mbox{}\verb@                           Counter>& lhs,@\\
\mbox{}\verb@    const iterator_counter<Iterator, Difference, @\\
\mbox{}\verb@                           Counter>& rhs) {@\\
\mbox{}\verb@  ++iterator_counter<Iterator, Difference, @\\
\mbox{}\verb@                     Counter>::counters[LESS_THAN];@\\
\mbox{}\verb@  return rhs.base_iterator < lhs.base_iterator;@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@\\
\mbox{}\verb@template <typename Iterator, typename Difference, @\\
\mbox{}\verb@          typename Counter>@\\
\mbox{}\verb@bool operator<=(@\\
\mbox{}\verb@    const iterator_counter<Iterator, Difference, @\\
\mbox{}\verb@                           Counter>& lhs,@\\
\mbox{}\verb@    const iterator_counter<Iterator, Difference, @\\
\mbox{}\verb@                           Counter>& rhs) {@\\
\mbox{}\verb@  ++iterator_counter<Iterator, Difference, @\\
\mbox{}\verb@                     Counter>::counters[LESS_THAN];@\\
\mbox{}\verb@  return !(rhs.base_iterator < lhs.base_iterator);@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@\\
\mbox{}\verb@template <typename Iterator, typename Difference, @\\
\mbox{}\verb@          typename Counter>@\\
\mbox{}\verb@bool operator>=(@\\
\mbox{}\verb@    const iterator_counter<Iterator, Difference, @\\
\mbox{}\verb@                           Counter>& lhs,@\\
\mbox{}\verb@    const iterator_counter<Iterator, Difference, @\\
\mbox{}\verb@                           Counter>& rhs) {@\\
\mbox{}\verb@  ++iterator_counter<Iterator, Difference, @\\
\mbox{}\verb@                     Counter>::counters[LESS_THAN];@\\
\mbox{}\verb@  return !(lhs.base_iterator < rhs.base_iterator);@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@template <typename Iterator, typename Difference,@\\
\mbox{}\verb@          typename Counter, @\\
\mbox{}\verb@          typename Predicate, typename T>@\\
\mbox{}\verb@inline iterator_counter<Iterator, Difference, Counter>@\\
\mbox{}\verb@  __stable_partition_aux(@\\
\mbox{}\verb@    iterator_counter<Iterator, Difference,@\\
\mbox{}\verb@                     Counter> first,@\\
\mbox{}\verb@    iterator_counter<Iterator, Difference, @\\
\mbox{}\verb@                     Counter> last,@\\
\mbox{}\verb@    Predicate pred, T*, Difference*) {@\\
\mbox{}\verb@@\\
\mbox{}\verb@  _Temporary_buffer<@\\
\mbox{}\verb@    iterator_counter<Iterator, Difference, Counter>, T> @\\
\mbox{}\verb@    buf(first, last);@\\
\mbox{}\verb@  if (buf.size() > 0)@\\
\mbox{}\verb@    return __stable_partition_adaptive(first, last, pred,@\\
\mbox{}\verb@                   Difference(buf.requested_size()),@\\
\mbox{}\verb@                   buf.begin(),@\\
\mbox{}\verb@                   // conversion to Difference added@\\
\mbox{}\verb@                   Difference(buf.size()));@\\
\mbox{}\verb@  else@\\
\mbox{}\verb@    return __inplace_stable_partition(first, last, pred, @\\
\mbox{}\verb@                   Difference(buf.requested_size()));@\\
\mbox{}\verb@}@\\
\mbox{}\verb@template <typename Value, typename Counter>@\\
\mbox{}\verb@class value_counter;@\\
\mbox{}\verb@template <typename Value, typename Counter>@\\
\mbox{}\verb@bool operator==(@\\
\mbox{}\verb@    const value_counter<Value, Counter>& lhs, @\\
\mbox{}\verb@    const value_counter<Value, Counter>& rhs);@\\
\mbox{}\verb@template <typename Value, typename Counter>@\\
\mbox{}\verb@bool operator!=(@\\
\mbox{}\verb@    const value_counter<Value, Counter>& lhs, @\\
\mbox{}\verb@    const value_counter<Value, Counter>& rhs);@\\
\mbox{}\verb@template <typename Value, typename Counter>@\\
\mbox{}\verb@bool operator<(@\\
\mbox{}\verb@    const value_counter<Value, Counter>& lhs, @\\
\mbox{}\verb@    const value_counter<Value, Counter>& rhs);@\\
\mbox{}\verb@template <typename Value, typename Counter>@\\
\mbox{}\verb@bool operator>(@\\
\mbox{}\verb@    const value_counter<Value, Counter>& lhs, @\\
\mbox{}\verb@    const value_counter<Value, Counter>& rhs);@\\
\mbox{}\verb@template <typename Value, typename Counter>@\\
\mbox{}\verb@bool operator<=(@\\
\mbox{}\verb@    const value_counter<Value, Counter>& lhs, @\\
\mbox{}\verb@    const value_counter<Value, Counter>& rhs);@\\
\mbox{}\verb@template <typename Value, typename Counter>@\\
\mbox{}\verb@bool operator>=(@\\
\mbox{}\verb@    const value_counter<Value, Counter>& lhs, @\\
\mbox{}\verb@    const value_counter<Value, Counter>& rhs);@\\
\mbox{}\verb@@\\
\mbox{}\verb@template <typename Value,@\\
\mbox{}\verb@          typename Counter = DEFAULT_COUNTER_TYPE>@\\
\mbox{}\verb@class value_counter {@\\
\mbox{}\verb@ public:@\\
\mbox{}\verb@  typedef Value value_type;@\\
\mbox{}\verb@  typedef Counter counter_type;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  value_counter() : base_value(), generation(0) {@\\
\mbox{}\verb@    ++counters[DEFAULT_CTOR];@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  value_counter(const value_counter& x)@\\
\mbox{}\verb@    : base_value(x.base_value), generation(x.generation + 1) {@\\
\mbox{}\verb@    ++counters[COPY_CTOR];@\\
\mbox{}\verb@    counters[GENERATION] = std::max(counters[GENERATION], @\\
\mbox{}\verb@                                    generation);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  explicit value_counter(const value_type& x) @\\
\mbox{}\verb@    : base_value(x), generation(0) {@\\
\mbox{}\verb@    ++counters[OTHER_CTOR];@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  ~value_counter() {@\\
\mbox{}\verb@    ++counters[DTOR]; @\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  value_counter& operator=(const value_counter& x) {@\\
\mbox{}\verb@    ++counters[ASSIGNMENT];@\\
\mbox{}\verb@    base_value = x.base_value;@\\
\mbox{}\verb@    generation = x.generation;@\\
\mbox{}\verb@    return *this;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  value_type& base() {@\\
\mbox{}\verb@    ++counters[BASE];@\\
\mbox{}\verb@    return base_value;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  const value_type& base() const {@\\
\mbox{}\verb@    ++counters[BASE];@\\
\mbox{}\verb@    return base_value;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@@\\
\mbox{}\verb@  friend bool operator== <Value, Counter>(@\\
\mbox{}\verb@      const value_counter& lhs, @\\
\mbox{}\verb@      const value_counter& rhs);@\\
\mbox{}\verb@  friend bool operator!= <Value, Counter>(@\\
\mbox{}\verb@      const value_counter& lhs, @\\
\mbox{}\verb@      const value_counter& rhs);@\\
\mbox{}\verb@  friend bool operator< <Value, Counter>(@\\
\mbox{}\verb@      const value_counter& lhs, @\\
\mbox{}\verb@      const value_counter& rhs);@\\
\mbox{}\verb@  friend bool operator> <Value, Counter>(@\\
\mbox{}\verb@      const value_counter& lhs, @\\
\mbox{}\verb@      const value_counter& rhs);@\\
\mbox{}\verb@  friend bool operator<= <Value, Counter>(@\\
\mbox{}\verb@      const value_counter& lhs, @\\
\mbox{}\verb@      const value_counter& rhs);@\\
\mbox{}\verb@  friend bool operator>= <Value, Counter>(@\\
\mbox{}\verb@      const value_counter& lhs, @\\
\mbox{}\verb@      const value_counter& rhs);@\\
\mbox{}\verb@@\\
\mbox{}\verb@ protected:@\\
\mbox{}\verb@  value_type base_value;@\\
\mbox{}\verb@  Counter generation;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  static typename recorder<Counter>::counter_vector_type& @\\
\mbox{}\verb@         counters;@\\
\mbox{}\verb@};@\\
\mbox{}\verb@@\\
\mbox{}\verb@template <typename Value, typename Counter>@\\
\mbox{}\verb@  typename recorder<Counter>::counter_vector_type&@\\
\mbox{}\verb@    value_counter<Value, Counter>::counters =@\\
\mbox{}\verb@      *recorder<Counter>::create("value_counter");@\\
\mbox{}\verb@@\\
\mbox{}\verb@template <typename Value, typename Counter>@\\
\mbox{}\verb@bool operator==(@\\
\mbox{}\verb@    const value_counter<Value, Counter>& lhs, @\\
\mbox{}\verb@    const value_counter<Value, Counter>& rhs) {@\\
\mbox{}\verb@  ++value_counter<Value, Counter>::counters[EQUALITY];@\\
\mbox{}\verb@  return lhs.base_value == rhs.base_value;@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@\\
\mbox{}\verb@template <typename Value, typename Counter>@\\
\mbox{}\verb@bool operator!=(@\\
\mbox{}\verb@    const value_counter<Value, Counter>& lhs, @\\
\mbox{}\verb@    const value_counter<Value, Counter>& rhs) {@\\
\mbox{}\verb@  ++value_counter<Value, Counter>::counters[EQUALITY];@\\
\mbox{}\verb@  return !(lhs.base_value == rhs.base_value);@\\
\mbox{}\verb@}@\\
\mbox{}\verb@template <typename Value, typename Counter>@\\
\mbox{}\verb@bool operator<(@\\
\mbox{}\verb@    const value_counter<Value, Counter>& lhs, @\\
\mbox{}\verb@    const value_counter<Value, Counter>& rhs) {@\\
\mbox{}\verb@  ++value_counter<Value, Counter>::counters[LESS_THAN];@\\
\mbox{}\verb@  return lhs.base_value < rhs.base_value;@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@\\
\mbox{}\verb@template <typename Value, typename Counter>@\\
\mbox{}\verb@bool operator>(@\\
\mbox{}\verb@    const value_counter<Value, Counter>& lhs, @\\
\mbox{}\verb@    const value_counter<Value, Counter>& rhs) {@\\
\mbox{}\verb@  ++value_counter<Value, Counter>::counters[LESS_THAN];@\\
\mbox{}\verb@  return rhs.base_value < lhs.base_value;@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@\\
\mbox{}\verb@template <typename Value, typename Counter>@\\
\mbox{}\verb@bool operator<=(@\\
\mbox{}\verb@    const value_counter<Value, Counter>& lhs, @\\
\mbox{}\verb@    const value_counter<Value, Counter>& rhs) {@\\
\mbox{}\verb@  ++value_counter<Value, Counter>::counters[LESS_THAN];@\\
\mbox{}\verb@  return !(rhs.base_value < lhs.base_value);@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@\\
\mbox{}\verb@template <typename Value, typename Counter>@\\
\mbox{}\verb@bool operator>=(@\\
\mbox{}\verb@    const value_counter<Value, Counter>& lhs, @\\
\mbox{}\verb@    const value_counter<Value, Counter>& rhs) {@\\
\mbox{}\verb@  ++value_counter<Value, Counter>::counters[LESS_THAN];@\\
\mbox{}\verb@  return !(lhs.base_value < rhs.base_value);@\\
\mbox{}\verb@}@\\
\mbox{}\verb@template <typename AdaptableGenerator,@\\
\mbox{}\verb@          typename Counter = DEFAULT_COUNTER_TYPE>@\\
\mbox{}\verb@class generator_counter {@\\
\mbox{}\verb@ public:@\\
\mbox{}\verb@  typedef AdaptableGenerator function_type;@\\
\mbox{}\verb@  typedef Counter counter_type;@\\
\mbox{}\verb@  typedef typename AdaptableGenerator::result_type result_type;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  generator_counter() : base_function(), generation(0) { @\\
\mbox{}\verb@    ++counters[DEFAULT_CTOR]; @\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  generator_counter(const generator_counter& x)@\\
\mbox{}\verb@    : base_function(x.base_function), @\\
\mbox{}\verb@      generation(x.generation + 1) {@\\
\mbox{}\verb@    ++counters[COPY_CTOR];@\\
\mbox{}\verb@    counters[GENERATION] = max(counters[GENERATION], generation);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  explicit generator_counter(const function_type& x) @\\
\mbox{}\verb@    : base_function(x), generation(0) {@\\
\mbox{}\verb@    ++counters[OTHER_CTOR]; @\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  ~generator_counter() { @\\
\mbox{}\verb@    ++counters[DTOR]; @\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  generator_counter& operator=(const generator_counter& x) { @\\
\mbox{}\verb@    ++counters[ASSIGNMENT]; @\\
\mbox{}\verb@    base_function = rhs.base_function;@\\
\mbox{}\verb@    generation = x.generation;@\\
\mbox{}\verb@    return *this;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  function_type& base() { @\\
\mbox{}\verb@    ++counters[BASE];@\\
\mbox{}\verb@    return base_function; @\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  const function_type& base() const { @\\
\mbox{}\verb@    ++counters[BASE];@\\
\mbox{}\verb@    return base_function; @\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  result_type operator()() {@\\
\mbox{}\verb@    ++counters[FUNCTION_CALL];@\\
\mbox{}\verb@    return base_function();@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  result_type operator()() const {@\\
\mbox{}\verb@    ++counters[FUNCTION_CALL];@\\
\mbox{}\verb@    return base_function();@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@@\\
\mbox{}\verb@ protected:@\\
\mbox{}\verb@  function_type base_function;@\\
\mbox{}\verb@  Counter generation;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  static typename recorder<Counter>::counter_vector_type& @\\
\mbox{}\verb@         counters;@\\
\mbox{}\verb@};@\\
\mbox{}\verb@@\\
\mbox{}\verb@template <typename AdaptableGenerator, typename Counter>@\\
\mbox{}\verb@  typename recorder<Counter>::counter_vector_type&@\\
\mbox{}\verb@    generator_counter<AdaptableGenerator, @\\
\mbox{}\verb@                      Counter>::counters =@\\
\mbox{}\verb@      *recorder<Counter>::create("generator_counter");@\\
\mbox{}\verb@template <typename AdaptableGenerator>@\\
\mbox{}\verb@  generator_counter<AdaptableGenerator> function_counter(@\\
\mbox{}\verb@    const AdaptableGenerator& x) {@\\
\mbox{}\verb@  return generator_counter<AdaptableGenerator>(x);@\\
\mbox{}\verb@}@\\
\mbox{}\verb@template <typename AdaptableUnaryFunction,@\\
\mbox{}\verb@          typename Counter = DEFAULT_COUNTER_TYPE>@\\
\mbox{}\verb@class unary_function_counter @\\
\mbox{}\verb@  : public std::unary_function<@\\
\mbox{}\verb@        typename AdaptableUnaryFunction::argument_type,@\\
\mbox{}\verb@        typename AdaptableUnaryFunction::result_type> {@\\
\mbox{}\verb@ public:@\\
\mbox{}\verb@  typedef AdaptableUnaryFunction function_type;@\\
\mbox{}\verb@  typedef typename AdaptableUnaryFunction::argument_type @\\
\mbox{}\verb@      argument_type;@\\
\mbox{}\verb@  typedef typename AdaptableUnaryFunction::result_type @\\
\mbox{}\verb@      result_type;@\\
\mbox{}\verb@  typedef Counter counter_type;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  unary_function_counter() : base_function(), generation(0) { @\\
\mbox{}\verb@    ++counters[DEFAULT_CTOR]; @\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  unary_function_counter(const unary_function_counter& x)@\\
\mbox{}\verb@    : base_function(x.base_function), @\\
\mbox{}\verb@      generation(x.generation + 1) {@\\
\mbox{}\verb@    ++counters[COPY_CTOR];@\\
\mbox{}\verb@    counters[GENERATION] = max(counters[GENERATION], generation);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  explicit unary_function_counter(const function_type& x) @\\
\mbox{}\verb@    : base_function(x), generation(0) {@\\
\mbox{}\verb@    ++counters[OTHER_CTOR]; @\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  ~unary_function_counter() {@\\
\mbox{}\verb@    ++counters[DTOR];@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  unary_function_counter& @\\
\mbox{}\verb@    operator=(const unary_function_counter& x) { @\\
\mbox{}\verb@    ++counters[ASSIGNMENT]; @\\
\mbox{}\verb@    base_function = x.base_function;@\\
\mbox{}\verb@    generation = x.generation;@\\
\mbox{}\verb@    return *this;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  function_type& base() { @\\
\mbox{}\verb@    ++counters[BASE];@\\
\mbox{}\verb@    return base_function; @\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  const function_type& base() const { @\\
\mbox{}\verb@    ++counters[BASE];@\\
\mbox{}\verb@            return base_function; @\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  result_type operator()(const argument_type& arg) const {@\\
\mbox{}\verb@    ++counters[FUNCTION_CALL];@\\
\mbox{}\verb@    return base_function(arg);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@@\\
\mbox{}\verb@ protected:@\\
\mbox{}\verb@  function_type base_function;@\\
\mbox{}\verb@  Counter generation;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  static typename recorder<Counter>::counter_vector_type& @\\
\mbox{}\verb@         counters;@\\
\mbox{}\verb@};@\\
\mbox{}\verb@@\\
\mbox{}\verb@template <typename AdaptableUnaryFunction, @\\
\mbox{}\verb@          typename Counter>@\\
\mbox{}\verb@  typename recorder<Counter>::counter_vector_type&@\\
\mbox{}\verb@    unary_function_counter<AdaptableUnaryFunction, @\\
\mbox{}\verb@                           Counter>::counters =@\\
\mbox{}\verb@      *recorder<Counter>::create("unary_function_counter");@\\
\mbox{}\verb@template <typename AdaptableUnaryFunction>@\\
\mbox{}\verb@  unary_function_counter<AdaptableUnaryFunction>@\\
\mbox{}\verb@    function_counter1(@\\
\mbox{}\verb@    const AdaptableUnaryFunction& x) {@\\
\mbox{}\verb@  return unary_function_counter<AdaptableUnaryFunction>(x);@\\
\mbox{}\verb@}@\\
\mbox{}\verb@template <typename AdaptableBinaryFunction,@\\
\mbox{}\verb@          typename Counter = DEFAULT_COUNTER_TYPE>@\\
\mbox{}\verb@class binary_function_counter @\\
\mbox{}\verb@  : public std::binary_function<@\\
\mbox{}\verb@        typename AdaptableBinaryFunction::first_argument_type,@\\
\mbox{}\verb@        typename AdaptableBinaryFunction::second_argument_type,@\\
\mbox{}\verb@        typename AdaptableBinaryFunction::result_type> {@\\
\mbox{}\verb@ public:@\\
\mbox{}\verb@  typedef AdaptableBinaryFunction function_type;@\\
\mbox{}\verb@  typedef typename AdaptableBinaryFunction::first_argument_type @\\
\mbox{}\verb@      first_argument_type;@\\
\mbox{}\verb@  typedef typename AdaptableBinaryFunction::second_argument_type@\\
\mbox{}\verb@      second_argument_type;@\\
\mbox{}\verb@  typedef typename AdaptableBinaryFunction::result_type @\\
\mbox{}\verb@      result_type;@\\
\mbox{}\verb@  typedef Counter counter_type;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  binary_function_counter() : base_function(), generation(0) { @\\
\mbox{}\verb@    ++counters[DEFAULT_CTOR]; @\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  binary_function_counter(const binary_function_counter& x)@\\
\mbox{}\verb@    : base_function(x.base_function), @\\
\mbox{}\verb@      generation(x.generation + 1) {@\\
\mbox{}\verb@    ++counters[COPY_CTOR];@\\
\mbox{}\verb@    counters[GENERATION] = max(counters[GENERATION], generation);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  explicit binary_function_counter(const function_type& x) @\\
\mbox{}\verb@    : base_function(x), generation(0) {@\\
\mbox{}\verb@    ++counters[OTHER_CTOR]; @\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  ~binary_function_counter() { @\\
\mbox{}\verb@    ++counters[DTOR]; @\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  binary_function_counter& @\\
\mbox{}\verb@    operator=(const binary_function_counter& x) { @\\
\mbox{}\verb@    ++counters[ASSIGNMENT]; @\\
\mbox{}\verb@    base_function = x.base_function;@\\
\mbox{}\verb@    generation = x.generation;@\\
\mbox{}\verb@    return *this;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  function_type& base() { @\\
\mbox{}\verb@    ++counters[BASE];@\\
\mbox{}\verb@    return base_function; @\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  const function_type& base() const { @\\
\mbox{}\verb@    ++counters[BASE];@\\
\mbox{}\verb@    return base_function; @\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  result_type operator()(const first_argument_type& x,@\\
\mbox{}\verb@                         const second_argument_type& y) const {@\\
\mbox{}\verb@    ++counters[FUNCTION_CALL];@\\
\mbox{}\verb@    return base_function(x, y);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@@\\
\mbox{}\verb@ protected:@\\
\mbox{}\verb@  function_type base_function;@\\
\mbox{}\verb@  Counter generation;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  static typename recorder<Counter>::counter_vector_type& @\\
\mbox{}\verb@         counters;@\\
\mbox{}\verb@};@\\
\mbox{}\verb@                      @\\
\mbox{}\verb@template <typename AdaptableBinaryFunction,@\\
\mbox{}\verb@          typename Counter>@\\
\mbox{}\verb@  typename recorder<Counter>::counter_vector_type&@\\
\mbox{}\verb@    binary_function_counter<AdaptableBinaryFunction, @\\
\mbox{}\verb@                            Counter>::counters =@\\
\mbox{}\verb@      *recorder<Counter>::create("binary_function_counter");@\\
\mbox{}\verb@template <typename AdaptableBinaryFunction>@\\
\mbox{}\verb@  binary_function_counter<AdaptableBinaryFunction> @\\
\mbox{}\verb@    function_counter2(@\\
\mbox{}\verb@    const AdaptableBinaryFunction& x) {@\\
\mbox{}\verb@  return binary_function_counter<AdaptableBinaryFunction>(x);@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@\\
\mbox{}\verb@#endif  // COUNTERS_H@\\
\mbox{}\verb@@
\end{list}
\vspace{-2ex}
\end{flushleft}
\section{Test 1}
\subsection{Test 1a}
\label{sec-code-count-1a}
\begin{flushleft} \small \label{part101}
\verb@"opcount_test1a.cpp"@ {\footnotesize \hypertarget{174}{174} }$\equiv$
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@#include <cmath>@\\
\mbox{}\verb@#include <cstdlib>@\\
\mbox{}\verb@#include <ctime>@\\
\mbox{}\verb@#include <iostream>@\\
\mbox{}\verb@#include <vector>@\\
\mbox{}\verb@#include <algorithm>@\\
\mbox{}\verb@#include <iostream>@\\
\mbox{}\verb@#include <vector>@\\
\mbox{}\verb@#include <list>@\\
\mbox{}\verb@#include <iterator>@\\
\mbox{}\verb@@\\
\mbox{}\verb@#include "timer.h"@\\
\mbox{}\verb@@\\
\mbox{}\verb@#define DEFAULT_COUNTER_TYPE int@\\
\mbox{}\verb@#include "counters.h"@\\
\mbox{}\verb@#include "router.hpp"@\\
\mbox{}\verb@@\\
\mbox{}\verb@using std::cout;@\\
\mbox{}\verb@using std::endl;@\\
\mbox{}\verb@using std::vector;@\\
\mbox{}\verb@using std::list;@\\
\mbox{}\verb@using std::back_inserter;@\\
\mbox{}\verb@using std::ostream_iterator;@\\
\mbox{}\verb@using std::back_insert_iterator;@\\
\mbox{}\verb@@\\
\mbox{}\verb@using gdfa::router;@\\
\mbox{}\verb@using gdfa::destination;@\\
\mbox{}\verb@@\\
\mbox{}\verb@using namespace counters;@\\
\mbox{}\verb@@\\
\mbox{}\verb@template <typename OutputIterator>@\\
\mbox{}\verb@class less_than_n : public destination<value_counter<int> >@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  private:@\\
\mbox{}\verb@    OutputIterator out;@\\
\mbox{}\verb@    value_counter<int> n;@\\
\mbox{}\verb@    @\\
\mbox{}\verb@  public:@\\
\mbox{}\verb@    less_than_n(OutputIterator _out, int _n) : out(_out), n(_n) {}@\\
\mbox{}\verb@    @\\
\mbox{}\verb@    bool distribute(const value_counter<int> & element)@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      if (element < n)@\\
\mbox{}\verb@      {@\\
\mbox{}\verb@        *(out++) = element;@\\
\mbox{}\verb@        return false;//continue filtering@\\
\mbox{}\verb@      }@\\
\mbox{}\verb@      @\\
\mbox{}\verb@      return false;    @\\
\mbox{}\verb@    }@\\
\mbox{}\verb@};@\\
\mbox{}\verb@@\\
\mbox{}\verb@template <typename OutputIterator>@\\
\mbox{}\verb@class my_default : public destination<value_counter<int> >@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  private:@\\
\mbox{}\verb@    OutputIterator out;@\\
\mbox{}\verb@    @\\
\mbox{}\verb@  public:@\\
\mbox{}\verb@    my_default(OutputIterator _out) : out(_out) {}@\\
\mbox{}\verb@    @\\
\mbox{}\verb@    bool distribute(const value_counter<int> & n)@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      *(out++) = n;@\\
\mbox{}\verb@      return true;@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@};@\\
\mbox{}\verb@@\\
\mbox{}\verb@void test() {@\\
\mbox{}\verb@  cout<<"Test 1a\nTesting N\nTiming distribute on integers.\n";@\\
\mbox{}\verb@  cout<<"Distribute to all destinations." << endl;@\\
\mbox{}\verb@ srand(time(0));@\\
\mbox{}\verb@  typedef counters::iterator_counter<vector@\\
\mbox{}\verb@   <value_counter<int> >::iterator> citer;@\\
\mbox{}\verb@  //typedef the counter vector@\\
\mbox{}\verb@  typedef vector<value_counter<int> > count_vector;@\\
\mbox{}\verb@  // Initial Setup@\\
\mbox{}\verb@  router<value_counter<int> > *r;@\\
\mbox{}\verb@  r = new router<value_counter<int> >;@\\
\mbox{}\verb@  //vectors of counter_ints@\\
\mbox{}\verb@  count_vector v, out1, out2, out3, defaultItems;@\\
\mbox{}\verb@  //vectors of counter_ints@\\
\mbox{}\verb@  count_vector out1_saved, out2_saved, defaultItems_saved;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  //back_insert_iterator of count_vector@\\
\mbox{}\verb@  typedef std::back_insert_iterator<count_vector> BItype;@\\
\mbox{}\verb@    delete r;@\\
\mbox{}\verb@    r = new router<value_counter<int> >;@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  out1.clear();@\\
\mbox{}\verb@  out2.clear();@\\
\mbox{}\verb@  out3.clear();@\\
\mbox{}\verb@  defaultItems.clear();@\\
\mbox{}\verb@@\\
\mbox{}\verb@  less_than_n<BItype> test1(back_inserter(out1), 1048576);@\\
\mbox{}\verb@  less_than_n<BItype> test2(back_inserter(out2), 1048576);@\\
\mbox{}\verb@  less_than_n<BItype> test3(back_inserter(out3), 1048576);@\\
\mbox{}\verb@  my_default<BItype> defaultTest(back_inserter(defaultItems)); @\\
\mbox{}\verb@  @\\
\mbox{}\verb@  r->add_destination(test1);@\\
\mbox{}\verb@  r->add_destination(test2);@\\
\mbox{}\verb@  r->add_destination(test3);@\\
\mbox{}\verb@  r->set_default(defaultTest);@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@  unsigned long N, N1, N2;@\\
\mbox{}\verb@  unsigned int reps;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  N1 = 1;@\\
\mbox{}\verb@  N2 = 1048576;@\\
\mbox{}\verb@//  N2 = 1048576;@\\
\mbox{}\verb@  reps = 1;@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@  //now we need to print the results@\\
\mbox{}\verb@  /*this code is from quantiles-count.cpp, by DRM,@\\
\mbox{}\verb@  http://www.cs.rpi.edu/~musser/gsd/quantiles/quantiles-count.cpp@\\
\mbox{}\verb@  this code sets up the operations counting and reporting*/@\\
\mbox{}\verb@  counters::operator_type group0[] = { @\\
\mbox{}\verb@    counters::LESS_THAN, counters::EQUALITY,@\\
\mbox{}\verb@  };@\\
\mbox{}\verb@  counters::operator_type group1[] = { @\\
\mbox{}\verb@    counters::DEFAULT_CTOR, @\\
\mbox{}\verb@    counters::COPY_CTOR, @\\
\mbox{}\verb@    counters::OTHER_CTOR, @\\
\mbox{}\verb@    counters::ASSIGNMENT,@\\
\mbox{}\verb@  };@\\
\mbox{}\verb@  counters::operator_type group2[] = { @\\
\mbox{}\verb@    counters::CONVERSION, counters::POST_INCREMENT, @\\
\mbox{}\verb@    counters::PRE_INCREMENT, @\\
\mbox{}\verb@    counters::POST_DECREMENT, counters::PRE_DECREMENT, @\\
\mbox{}\verb@    counters::UNARY_PLUS, counters::UNARY_MINUS, @\\
\mbox{}\verb@    counters::PLUS, counters::MINUS, counters::TIMES, @\\
\mbox{}\verb@    counters::DIVIDE, counters::MODULO,@\\
\mbox{}\verb@    counters::LEFT_SHIFT, counters::RIGHT_SHIFT,@\\
\mbox{}\verb@    counters::PLUS_ASSIGN, counters::MINUS_ASSIGN, @\\
\mbox{}\verb@    counters::TIMES_ASSIGN, counters::DIVIDE_ASSIGN, @\\
\mbox{}\verb@    counters::MODULO_ASSIGN,@\\
\mbox{}\verb@    counters::LEFT_SHIFT_ASSIGN, counters::RIGHT_SHIFT_ASSIGN,@\\
\mbox{}\verb@    counters::DEREFERENCE, counters::MEMBER, @\\
\mbox{}\verb@    counters::SUBSCRIPT, counters::FUNCTION_CALL,@\\
\mbox{}\verb@    counters::NEGATE, counters::AND, counters::AND_ASSIGN, @\\
\mbox{}\verb@    counters::OR, counters::OR_ASSIGN, counters::XOR, @\\
\mbox{}\verb@    counters::XOR_ASSIGN,@\\
\mbox{}\verb@  };@\\
\mbox{}\verb@  counters::operator_type group3[] = { @\\
\mbox{}\verb@    counters::BASE, @\\
\mbox{}\verb@    counters::DTOR, @\\
\mbox{}\verb@    counters::GENERATION, @\\
\mbox{}\verb@  };@\\
\mbox{}\verb@  //  counters::scale_recorder_visitor<@\\
\mbox{}\verb@  //    counters::group_recorder_visitor<> > my_visitor(0.001);@\\
\mbox{}\verb@  counters::group_recorder_visitor<> my_visitor;@\\
\mbox{}\verb@  my_visitor.add("Compare", group0, @\\
\mbox{}\verb@              group0 + sizeof(group0) / sizeof(group0[0]));@\\
\mbox{}\verb@  my_visitor.add("Assign", group1, @\\
\mbox{}\verb@              group1 + sizeof(group1) / sizeof(group1[0]));@\\
\mbox{}\verb@  my_visitor.add("Other", group2, @\\
\mbox{}\verb@              group2 + sizeof(group2) / sizeof(group2[0]));@\\
\mbox{}\verb@  my_visitor.hide(group3, @\\
\mbox{}\verb@               group3 + sizeof(group3) / sizeof(group3[0]));@\\
\mbox{}\verb@@\\
\mbox{}\verb@  recorder<> my_recorder;@\\
\mbox{}\verb@  my_recorder.clear();@\\
\mbox{}\verb@@\\
\mbox{}\verb@  for (N = N1; N <= N2; N *= 2)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    cout<<N<<endl;@\\
\mbox{}\verb@    my_recorder.pause();@\\
\mbox{}\verb@    v.clear(); @\\
\mbox{}\verb@    v.reserve(N);@\\
\mbox{}\verb@    for (int i = 0; i < N; ++i)@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      v.push_back((value_counter<int>)i);@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@    out1.clear();@\\
\mbox{}\verb@    out2.clear();@\\
\mbox{}\verb@    out3.clear();@\\
\mbox{}\verb@    defaultItems.clear();@\\
\mbox{}\verb@    // End of Baseline Operations@\\
\mbox{}\verb@    ///////////////////////////////@\\
\mbox{}\verb@    // Main Timed Operation@\\
\mbox{}\verb@    my_recorder.resume();@\\
\mbox{}\verb@    r->distribute(citer(v.begin()), citer(v.end()));@\\
\mbox{}\verb@    my_recorder.record();@\\
\mbox{}\verb@    my_recorder.report(cout,my_visitor);@\\
\mbox{}\verb@    my_recorder.clear();@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@}@\\
\mbox{}\verb@@\\
\mbox{}\verb@int main()@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  test();  @\\
\mbox{}\verb@  return 0;@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@
\end{list}
\vspace{-2ex}
\end{flushleft}
\subsection{Test 1b}
\label{sec-code-count-1b}
\begin{flushleft} \small \label{part102}
\verb@"opcount_test1b.cpp"@ {\footnotesize \hypertarget{178}{178} }$\equiv$
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@#include <cmath>@\\
\mbox{}\verb@#include <cstdlib>@\\
\mbox{}\verb@#include <ctime>@\\
\mbox{}\verb@#include <iostream>@\\
\mbox{}\verb@#include <vector>@\\
\mbox{}\verb@#include <algorithm>@\\
\mbox{}\verb@#include <iostream>@\\
\mbox{}\verb@#include <vector>@\\
\mbox{}\verb@#include <list>@\\
\mbox{}\verb@#include <iterator>@\\
\mbox{}\verb@#include "timer.h"@\\
\mbox{}\verb@@\\
\mbox{}\verb@#define DEFAULT_COUNTER_TYPE int@\\
\mbox{}\verb@#include "counters.h"@\\
\mbox{}\verb@@\\
\mbox{}\verb@#include "router.hpp"@\\
\mbox{}\verb@@\\
\mbox{}\verb@using namespace std;@\\
\mbox{}\verb@using std::cout;@\\
\mbox{}\verb@using std::endl;@\\
\mbox{}\verb@using std::vector;@\\
\mbox{}\verb@using std::list;@\\
\mbox{}\verb@using std::back_inserter;@\\
\mbox{}\verb@using std::ostream_iterator;@\\
\mbox{}\verb@using std::back_insert_iterator;@\\
\mbox{}\verb@@\\
\mbox{}\verb@using namespace counters;@\\
\mbox{}\verb@using gdfa::router;@\\
\mbox{}\verb@using gdfa::destination;@\\
\mbox{}\verb@@\\
\mbox{}\verb@template <typename OutputIterator>@\\
\mbox{}\verb@class less_than_n : public destination<value_counter<int> >@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  private:@\\
\mbox{}\verb@    OutputIterator out;@\\
\mbox{}\verb@    value_counter<int> n;@\\
\mbox{}\verb@    @\\
\mbox{}\verb@  public:@\\
\mbox{}\verb@    less_than_n(OutputIterator _out, int _n) : out(_out), n(_n) {}@\\
\mbox{}\verb@    @\\
\mbox{}\verb@    bool distribute(const value_counter<int> & element)@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      if (element > n)@\\
\mbox{}\verb@      {@\\
\mbox{}\verb@        *(out++) = element;@\\
\mbox{}\verb@        return false;//continue filtering@\\
\mbox{}\verb@      }@\\
\mbox{}\verb@      @\\
\mbox{}\verb@      return false;    @\\
\mbox{}\verb@    }@\\
\mbox{}\verb@};@\\
\mbox{}\verb@@\\
\mbox{}\verb@template <typename OutputIterator>@\\
\mbox{}\verb@class my_default : public destination<value_counter<int> >@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  private:@\\
\mbox{}\verb@    OutputIterator out;@\\
\mbox{}\verb@    @\\
\mbox{}\verb@  public:@\\
\mbox{}\verb@    my_default(OutputIterator _out) : out(_out) {}@\\
\mbox{}\verb@    @\\
\mbox{}\verb@    bool distribute(const value_counter<int> & n)@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      *(out++) = n;@\\
\mbox{}\verb@      return true;@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@};@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@void test() {@\\
\mbox{}\verb@  cout<<"Test 1b\nTesting N\nTiming distribute on integers.\n";@\\
\mbox{}\verb@  cout<<"Distribute to just 1 of the destinations." << endl;@\\
\mbox{}\verb@  srand(time(0));@\\
\mbox{}\verb@@\\
\mbox{}\verb@  typedef counters::iterator_counter<@\\
\mbox{}\verb@   vector<value_counter<int> >::iterator> citer;@\\
\mbox{}\verb@  //typedef the counter vector@\\
\mbox{}\verb@  typedef vector<value_counter<int> > count_vector;@\\
\mbox{}\verb@  // Initial Setup@\\
\mbox{}\verb@  router<value_counter<int> > *r;@\\
\mbox{}\verb@  r = new router<value_counter<int> >;@\\
\mbox{}\verb@  count_vector v;@\\
\mbox{}\verb@  //vectors of counter_ints@\\
\mbox{}\verb@  count_vector out1, out2, out3, defaultItems;@\\
\mbox{}\verb@  //vectors of counter_ints@\\
\mbox{}\verb@  count_vector out1_saved, out2_saved, defaultItems_saved;@\\
\mbox{}\verb@@\\
\mbox{}\verb@    typedef std::back_insert_iterator<count_vector> BItype;@\\
\mbox{}\verb@    delete r;@\\
\mbox{}\verb@    r = new router<value_counter<int> >;@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  out1.clear();@\\
\mbox{}\verb@  out2.clear();@\\
\mbox{}\verb@  out3.clear();@\\
\mbox{}\verb@  defaultItems.clear();@\\
\mbox{}\verb@@\\
\mbox{}\verb@  less_than_n<BItype> test1(back_inserter(out1), 1048576);@\\
\mbox{}\verb@  less_than_n<BItype> test2(back_inserter(out2), 1048576);@\\
\mbox{}\verb@  less_than_n<BItype> test3(back_inserter(out3), 1048576);@\\
\mbox{}\verb@  my_default<BItype> defaultTest(back_inserter(defaultItems)); @\\
\mbox{}\verb@@\\
\mbox{}\verb@  r->add_destination(test1);@\\
\mbox{}\verb@  r->add_destination(test2);@\\
\mbox{}\verb@  r->add_destination(test3);@\\
\mbox{}\verb@  r->set_default(defaultTest);@\\
\mbox{}\verb@@\\
\mbox{}\verb@  //now we need to print the results@\\
\mbox{}\verb@  /*this code is from quantiles-count.cpp, by DRM,@\\
\mbox{}\verb@  http://www.cs.rpi.edu/~musser/gsd/quantiles/quantiles-count.cpp@\\
\mbox{}\verb@  this code sets up the operations counting and reporting*/@\\
\mbox{}\verb@  counters::operator_type group0[] = { @\\
\mbox{}\verb@    counters::LESS_THAN, counters::EQUALITY@\\
\mbox{}\verb@  };@\\
\mbox{}\verb@  counters::operator_type group1[] = { @\\
\mbox{}\verb@    counters::DEFAULT_CTOR, @\\
\mbox{}\verb@    counters::COPY_CTOR, @\\
\mbox{}\verb@    counters::OTHER_CTOR, @\\
\mbox{}\verb@    counters::ASSIGNMENT,@\\
\mbox{}\verb@  };@\\
\mbox{}\verb@  counters::operator_type group2[] = { @\\
\mbox{}\verb@    counters::CONVERSION, counters::POST_INCREMENT, @\\
\mbox{}\verb@    counters::PRE_INCREMENT, @\\
\mbox{}\verb@    counters::POST_DECREMENT, counters::PRE_DECREMENT, @\\
\mbox{}\verb@    counters::UNARY_PLUS, counters::UNARY_MINUS, @\\
\mbox{}\verb@    counters::PLUS, counters::MINUS, counters::TIMES, @\\
\mbox{}\verb@    counters::DIVIDE, counters::MODULO,@\\
\mbox{}\verb@    counters::LEFT_SHIFT, counters::RIGHT_SHIFT,@\\
\mbox{}\verb@    counters::PLUS_ASSIGN, counters::MINUS_ASSIGN, @\\
\mbox{}\verb@    counters::TIMES_ASSIGN, counters::DIVIDE_ASSIGN, @\\
\mbox{}\verb@    counters::MODULO_ASSIGN,@\\
\mbox{}\verb@    counters::LEFT_SHIFT_ASSIGN, counters::RIGHT_SHIFT_ASSIGN,@\\
\mbox{}\verb@    counters::DEREFERENCE, counters::MEMBER, @\\
\mbox{}\verb@    counters::SUBSCRIPT, counters::FUNCTION_CALL,@\\
\mbox{}\verb@    counters::NEGATE, counters::AND, counters::AND_ASSIGN, @\\
\mbox{}\verb@    counters::OR, counters::OR_ASSIGN, counters::XOR, @\\
\mbox{}\verb@    counters::XOR_ASSIGN,@\\
\mbox{}\verb@  };@\\
\mbox{}\verb@  counters::operator_type group3[] = { @\\
\mbox{}\verb@    counters::BASE, @\\
\mbox{}\verb@    counters::DTOR, @\\
\mbox{}\verb@    counters::GENERATION, @\\
\mbox{}\verb@  };@\\
\mbox{}\verb@  //  counters::scale_recorder_visitor<@\\
\mbox{}\verb@  //    counters::group_recorder_visitor<> > my_visitor(0.001);@\\
\mbox{}\verb@  counters::group_recorder_visitor<> my_visitor;@\\
\mbox{}\verb@  my_visitor.add("Compare", group0, @\\
\mbox{}\verb@              group0 + sizeof(group0) / sizeof(group0[0]));@\\
\mbox{}\verb@  my_visitor.add("Assign", group1, @\\
\mbox{}\verb@              group1 + sizeof(group1) / sizeof(group1[0]));@\\
\mbox{}\verb@  my_visitor.add("Other", group2, @\\
\mbox{}\verb@              group2 + sizeof(group2) / sizeof(group2[0]));@\\
\mbox{}\verb@  my_visitor.hide(group3, @\\
\mbox{}\verb@               group3 + sizeof(group3) / sizeof(group3[0]));@\\
\mbox{}\verb@@\\
\mbox{}\verb@  unsigned long N, N1, N2;@\\
\mbox{}\verb@  unsigned int reps;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  N1 = 1;@\\
\mbox{}\verb@  N2 = 1048576;@\\
\mbox{}\verb@//  N2 = 1048576;@\\
\mbox{}\verb@//  reps = 10;@\\
\mbox{}\verb@  reps = 1;@\\
\mbox{}\verb@  recorder<> my_recorder;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  for (N = N1; N <= N2; N *= 2)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    my_recorder.pause();@\\
\mbox{}\verb@    cout<<N<<endl;@\\
\mbox{}\verb@    v.clear(); @\\
\mbox{}\verb@    v.reserve(N);@\\
\mbox{}\verb@    for (int i = 0; i < N; ++i)@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      v.push_back((value_counter<int>)i);@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@@\\
\mbox{}\verb@    // Baseline Operations Here @\\
\mbox{}\verb@    out1.clear();@\\
\mbox{}\verb@    out2.clear();@\\
\mbox{}\verb@    out3.clear();@\\
\mbox{}\verb@    defaultItems.clear();@\\
\mbox{}\verb@    // End of Baseline Operations@\\
\mbox{}\verb@    ///////////////////////////////@\\
\mbox{}\verb@    // Main Timed Operation@\\
\mbox{}\verb@    my_recorder.resume();@\\
\mbox{}\verb@    r->distribute(citer(v.begin()),citer( v.end()));@\\
\mbox{}\verb@    //////////////////////////////////////@\\
\mbox{}\verb@    my_recorder.record();@\\
\mbox{}\verb@    my_recorder.report(cout,my_visitor);@\\
\mbox{}\verb@    my_recorder.clear();@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@\\
\mbox{}\verb@int main()@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  test();  @\\
\mbox{}\verb@  return 0;@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@
\end{list}
\vspace{-2ex}
\end{flushleft}
\section{Test 2}
\subsection{Test 2a}
\label{sec-code-count-2a}
\begin{flushleft} \small \label{part103}
\verb@"opcount_test2a.cpp"@ {\footnotesize \hypertarget{182}{182} }$\equiv$
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@#include <cmath>@\\
\mbox{}\verb@#include <cstdlib>@\\
\mbox{}\verb@#include <ctime>@\\
\mbox{}\verb@#include <iostream>@\\
\mbox{}\verb@#include <vector>@\\
\mbox{}\verb@#include <algorithm>@\\
\mbox{}\verb@#include <iostream>@\\
\mbox{}\verb@#include <vector>@\\
\mbox{}\verb@#include <list>@\\
\mbox{}\verb@#include <iterator>@\\
\mbox{}\verb@@\\
\mbox{}\verb@#include "timer.h"@\\
\mbox{}\verb@@\\
\mbox{}\verb@#define DEFAULT_COUNTER_TYPE int@\\
\mbox{}\verb@#include "counters.h"@\\
\mbox{}\verb@@\\
\mbox{}\verb@#include "router.hpp"@\\
\mbox{}\verb@@\\
\mbox{}\verb@using namespace std;@\\
\mbox{}\verb@using std::cout;@\\
\mbox{}\verb@using std::endl;@\\
\mbox{}\verb@using std::vector;@\\
\mbox{}\verb@using std::list;@\\
\mbox{}\verb@using std::back_inserter;@\\
\mbox{}\verb@using std::ostream_iterator;@\\
\mbox{}\verb@using std::back_insert_iterator;@\\
\mbox{}\verb@@\\
\mbox{}\verb@using namespace counters;@\\
\mbox{}\verb@using gdfa::router;@\\
\mbox{}\verb@using gdfa::destination;@\\
\mbox{}\verb@@\\
\mbox{}\verb@template <typename OutputIterator>@\\
\mbox{}\verb@class less_than_n : public destination<value_counter<int> >@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  private:@\\
\mbox{}\verb@    OutputIterator out;@\\
\mbox{}\verb@    value_counter<int>  n;@\\
\mbox{}\verb@    @\\
\mbox{}\verb@  public:@\\
\mbox{}\verb@    less_than_n(OutputIterator _out, int _n) : out(_out), n(_n) {}@\\
\mbox{}\verb@    @\\
\mbox{}\verb@    bool distribute(const value_counter<int> & element)@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      if (element > n)@\\
\mbox{}\verb@      {@\\
\mbox{}\verb@        *(out++) = element;@\\
\mbox{}\verb@        return false;// continue filtering@\\
\mbox{}\verb@      }@\\
\mbox{}\verb@      @\\
\mbox{}\verb@      return false;    @\\
\mbox{}\verb@    }@\\
\mbox{}\verb@};@\\
\mbox{}\verb@@\\
\mbox{}\verb@template <typename OutputIterator>@\\
\mbox{}\verb@class my_default : public destination<value_counter<int> >@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  private:@\\
\mbox{}\verb@    OutputIterator out;@\\
\mbox{}\verb@    @\\
\mbox{}\verb@  public:@\\
\mbox{}\verb@    my_default(OutputIterator _out) : out(_out) {}@\\
\mbox{}\verb@    @\\
\mbox{}\verb@    bool distribute(const value_counter<int> & n)@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      *(out) = n;@\\
\mbox{}\verb@      return true;@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@};@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@void test2() {@\\
\mbox{}\verb@  cout << "Test 2b\nTesting M\nTiming distribute on integers.\n";@\\
\mbox{}\verb@  cout<<"Distribute to just 1 of the destinations." << endl;@\\
\mbox{}\verb@  srand(time(0));@\\
\mbox{}\verb@@\\
\mbox{}\verb@  typedef counters::iterator_counter<@\\
\mbox{}\verb@   vector<value_counter<int> >::iterator> citer;@\\
\mbox{}\verb@  //typedef the counter vector@\\
\mbox{}\verb@  typedef vector<value_counter<int> > count_vector;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  // Initial Setup@\\
\mbox{}\verb@  router<value_counter<int> > *r;@\\
\mbox{}\verb@  r = new router<value_counter<int> >;@\\
\mbox{}\verb@  count_vector v, out1, out2, defaultItems;@\\
\mbox{}\verb@  count_vector out1_saved, out2_saved, defaultItems_saved;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  typedef std::back_insert_iterator<count_vector> BItype;@\\
\mbox{}\verb@    delete r;@\\
\mbox{}\verb@    r = new router<value_counter<int> >;@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  out1.clear();@\\
\mbox{}\verb@  out2.clear();@\\
\mbox{}\verb@  defaultItems.clear();@\\
\mbox{}\verb@@\\
\mbox{}\verb@  less_than_n<BItype> test1048576(back_inserter(out1), 1048576);@\\
\mbox{}\verb@  less_than_n<BItype> test20(back_inserter(out2), 20);@\\
\mbox{}\verb@  my_default<BItype> defaultTest(back_inserter(defaultItems)); @\\
\mbox{}\verb@  @\\
\mbox{}\verb@  r->set_default(defaultTest);@\\
\mbox{}\verb@  v.clear(); @\\
\mbox{}\verb@  v.reserve(10);@\\
\mbox{}\verb@  //    for (int i = 0; i < 100; ++i) {@\\
\mbox{}\verb@  for (int i = 0; i < 10; ++i) {@\\
\mbox{}\verb@    v.push_back((value_counter<int>)i);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@@\\
\mbox{}\verb@  //now we need to print the results@\\
\mbox{}\verb@  /*this code is from quantiles-count.cpp, by DRM,@\\
\mbox{}\verb@  http://www.cs.rpi.edu/~musser/gsd/quantiles/quantiles-count.cpp@\\
\mbox{}\verb@  this code sets up the operations counting and reporting*/@\\
\mbox{}\verb@  counters::operator_type group0[] = { @\\
\mbox{}\verb@    counters::LESS_THAN, counters::EQUALITY@\\
\mbox{}\verb@  };@\\
\mbox{}\verb@  counters::operator_type group1[] = { @\\
\mbox{}\verb@    counters::DEFAULT_CTOR, @\\
\mbox{}\verb@    counters::COPY_CTOR, @\\
\mbox{}\verb@    counters::OTHER_CTOR, @\\
\mbox{}\verb@    counters::ASSIGNMENT,@\\
\mbox{}\verb@  };@\\
\mbox{}\verb@  counters::operator_type group2[] = { @\\
\mbox{}\verb@    counters::CONVERSION, counters::POST_INCREMENT, @\\
\mbox{}\verb@    counters::PRE_INCREMENT, @\\
\mbox{}\verb@    counters::POST_DECREMENT, counters::PRE_DECREMENT, @\\
\mbox{}\verb@    counters::UNARY_PLUS, counters::UNARY_MINUS, @\\
\mbox{}\verb@    counters::PLUS, counters::MINUS, counters::TIMES, @\\
\mbox{}\verb@    counters::DIVIDE, counters::MODULO,@\\
\mbox{}\verb@    counters::LEFT_SHIFT, counters::RIGHT_SHIFT,@\\
\mbox{}\verb@    counters::PLUS_ASSIGN, counters::MINUS_ASSIGN, @\\
\mbox{}\verb@    counters::TIMES_ASSIGN, counters::DIVIDE_ASSIGN, @\\
\mbox{}\verb@    counters::MODULO_ASSIGN,@\\
\mbox{}\verb@    counters::LEFT_SHIFT_ASSIGN, counters::RIGHT_SHIFT_ASSIGN,@\\
\mbox{}\verb@    counters::DEREFERENCE, counters::MEMBER, @\\
\mbox{}\verb@    counters::SUBSCRIPT, counters::FUNCTION_CALL,@\\
\mbox{}\verb@    counters::NEGATE, counters::AND, counters::AND_ASSIGN, @\\
\mbox{}\verb@    counters::OR, counters::OR_ASSIGN, counters::XOR, @\\
\mbox{}\verb@    counters::XOR_ASSIGN,@\\
\mbox{}\verb@  };@\\
\mbox{}\verb@  counters::operator_type group3[] = { @\\
\mbox{}\verb@    counters::BASE, @\\
\mbox{}\verb@    counters::DTOR, @\\
\mbox{}\verb@    counters::GENERATION, @\\
\mbox{}\verb@  };@\\
\mbox{}\verb@  //  counters::scale_recorder_visitor<@\\
\mbox{}\verb@  //    counters::group_recorder_visitor<> > my_visitor(0.001);@\\
\mbox{}\verb@  counters::group_recorder_visitor<> my_visitor;@\\
\mbox{}\verb@  my_visitor.add("Compare", group0, @\\
\mbox{}\verb@              group0 + sizeof(group0) / sizeof(group0[0]));@\\
\mbox{}\verb@  my_visitor.add("Assign", group1, @\\
\mbox{}\verb@              group1 + sizeof(group1) / sizeof(group1[0]));@\\
\mbox{}\verb@  my_visitor.add("Other", group2, @\\
\mbox{}\verb@              group2 + sizeof(group2) / sizeof(group2[0]));@\\
\mbox{}\verb@  my_visitor.hide(group3, @\\
\mbox{}\verb@               group3 + sizeof(group3) / sizeof(group3[0]));@\\
\mbox{}\verb@@\\
\mbox{}\verb@  unsigned long N, N1, N2;@\\
\mbox{}\verb@  unsigned int reps;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  N1 = 1;@\\
\mbox{}\verb@  N2 = 1048576;@\\
\mbox{}\verb@  reps = 1;@\\
\mbox{}\verb@  recorder<> my_recorder;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  for (N = N1; N <= N2; N *= 2)@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      my_recorder.pause();@\\
\mbox{}\verb@      cout<<N<<endl;@\\
\mbox{}\verb@      @\\
\mbox{}\verb@      for (int i = 0; i < (N/2); ++i) {@\\
\mbox{}\verb@  r->add_destination(test1048576);@\\
\mbox{}\verb@      }@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@    //////////////////////////////  @\\
\mbox{}\verb@      // Baseline Operations Here @\\
\mbox{}\verb@    out1.clear();@\\
\mbox{}\verb@    defaultItems.clear();@\\
\mbox{}\verb@           @\\
\mbox{}\verb@    // End of Baseline Operations@\\
\mbox{}\verb@    ///////////////////////////////@\\
\mbox{}\verb@    // Main Timed Operation@\\
\mbox{}\verb@    my_recorder.resume();@\\
\mbox{}\verb@    r->distribute(citer(v.begin()),citer( v.end()));@\\
\mbox{}\verb@    //////////////////////////////////////@\\
\mbox{}\verb@    my_recorder.record();@\\
\mbox{}\verb@    my_recorder.report(cout,my_visitor);@\\
\mbox{}\verb@    my_recorder.clear();@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@\\
\mbox{}\verb@int main()@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  test2();  @\\
\mbox{}\verb@  return 0;@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@
\end{list}
\vspace{-2ex}
\end{flushleft}
\subsection{Test 2b}
\label{sec-code-count-2b}
\begin{flushleft} \small \label{part104}
\verb@"opcount_test2b.cpp"@ {\footnotesize \hypertarget{186}{186} }$\equiv$
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@#include <cmath>@\\
\mbox{}\verb@#include <cstdlib>@\\
\mbox{}\verb@#include <ctime>@\\
\mbox{}\verb@#include <iostream>@\\
\mbox{}\verb@#include <vector>@\\
\mbox{}\verb@#include <algorithm>@\\
\mbox{}\verb@#include <iostream>@\\
\mbox{}\verb@#include <vector>@\\
\mbox{}\verb@#include <list>@\\
\mbox{}\verb@#include <iterator>@\\
\mbox{}\verb@@\\
\mbox{}\verb@#include "timer.h"@\\
\mbox{}\verb@@\\
\mbox{}\verb@#define DEFAULT_COUNTER_TYPE int@\\
\mbox{}\verb@#include "counters.h"@\\
\mbox{}\verb@@\\
\mbox{}\verb@#include "router.hpp"@\\
\mbox{}\verb@@\\
\mbox{}\verb@using namespace std;@\\
\mbox{}\verb@using std::cout;@\\
\mbox{}\verb@using std::endl;@\\
\mbox{}\verb@using std::vector;@\\
\mbox{}\verb@using std::list;@\\
\mbox{}\verb@using std::back_inserter;@\\
\mbox{}\verb@using std::ostream_iterator;@\\
\mbox{}\verb@using std::back_insert_iterator;@\\
\mbox{}\verb@@\\
\mbox{}\verb@using namespace counters;@\\
\mbox{}\verb@using gdfa::router;@\\
\mbox{}\verb@using gdfa::destination;@\\
\mbox{}\verb@@\\
\mbox{}\verb@template <typename OutputIterator>@\\
\mbox{}\verb@class less_than_n : public destination<value_counter<int> >@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  private:@\\
\mbox{}\verb@    OutputIterator out;@\\
\mbox{}\verb@    value_counter<int>  n;@\\
\mbox{}\verb@    @\\
\mbox{}\verb@  public:@\\
\mbox{}\verb@    less_than_n(OutputIterator _out, int _n) : out(_out), n(_n) {}@\\
\mbox{}\verb@    @\\
\mbox{}\verb@    bool distribute(const value_counter<int> & element)@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      if (element > n)@\\
\mbox{}\verb@      {@\\
\mbox{}\verb@        *(out++) = element;@\\
\mbox{}\verb@        return false;// continue filtering@\\
\mbox{}\verb@      }@\\
\mbox{}\verb@      @\\
\mbox{}\verb@      return false;    @\\
\mbox{}\verb@    }@\\
\mbox{}\verb@};@\\
\mbox{}\verb@@\\
\mbox{}\verb@template <typename OutputIterator>@\\
\mbox{}\verb@class my_default : public destination<value_counter<int> >@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  private:@\\
\mbox{}\verb@    OutputIterator out;@\\
\mbox{}\verb@    @\\
\mbox{}\verb@  public:@\\
\mbox{}\verb@    my_default(OutputIterator _out) : out(_out) {}@\\
\mbox{}\verb@    @\\
\mbox{}\verb@    bool distribute(const value_counter<int> & n)@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      *(out) = n;@\\
\mbox{}\verb@      return true;@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@};@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@void test2() {@\\
\mbox{}\verb@  cout << "Test 2b\nTesting M\nTiming distribute on integers.\n";@\\
\mbox{}\verb@  cout<<"Distribute to just 1 of the destinations." << endl;@\\
\mbox{}\verb@  srand(time(0));@\\
\mbox{}\verb@@\\
\mbox{}\verb@  typedef counters::iterator_counter<@\\
\mbox{}\verb@   vector<value_counter<int> >::iterator> citer;@\\
\mbox{}\verb@  //typedef the counter vector@\\
\mbox{}\verb@  typedef vector<value_counter<int> > count_vector;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  // Initial Setup@\\
\mbox{}\verb@  router<value_counter<int> > *r;@\\
\mbox{}\verb@  r = new router<value_counter<int> >;@\\
\mbox{}\verb@  count_vector v, out1, out2, defaultItems;@\\
\mbox{}\verb@  count_vector out1_saved, out2_saved, defaultItems_saved;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  typedef std::back_insert_iterator<count_vector> BItype;@\\
\mbox{}\verb@    delete r;@\\
\mbox{}\verb@    r = new router<value_counter<int> >;@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  out1.clear();@\\
\mbox{}\verb@  out2.clear();@\\
\mbox{}\verb@  defaultItems.clear();@\\
\mbox{}\verb@@\\
\mbox{}\verb@  less_than_n<BItype> test1048576(back_inserter(out1), 1048576);@\\
\mbox{}\verb@  less_than_n<BItype> test20(back_inserter(out2), 20);@\\
\mbox{}\verb@  my_default<BItype> defaultTest(back_inserter(defaultItems)); @\\
\mbox{}\verb@  @\\
\mbox{}\verb@  r->set_default(defaultTest);@\\
\mbox{}\verb@  v.clear(); @\\
\mbox{}\verb@  v.reserve(10);@\\
\mbox{}\verb@  //    for (int i = 0; i < 100; ++i) {@\\
\mbox{}\verb@  for (int i = 0; i < 10; ++i) {@\\
\mbox{}\verb@    v.push_back((value_counter<int>)i);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@@\\
\mbox{}\verb@  //now we need to print the results@\\
\mbox{}\verb@  /*this code is from quantiles-count.cpp, by DRM,@\\
\mbox{}\verb@  http://www.cs.rpi.edu/~musser/gsd/quantiles/quantiles-count.cpp@\\
\mbox{}\verb@  this code sets up the operations counting and reporting*/@\\
\mbox{}\verb@  counters::operator_type group0[] = { @\\
\mbox{}\verb@    counters::LESS_THAN, counters::EQUALITY@\\
\mbox{}\verb@  };@\\
\mbox{}\verb@  counters::operator_type group1[] = { @\\
\mbox{}\verb@    counters::DEFAULT_CTOR, @\\
\mbox{}\verb@    counters::COPY_CTOR, @\\
\mbox{}\verb@    counters::OTHER_CTOR, @\\
\mbox{}\verb@    counters::ASSIGNMENT,@\\
\mbox{}\verb@  };@\\
\mbox{}\verb@  counters::operator_type group2[] = { @\\
\mbox{}\verb@    counters::CONVERSION, counters::POST_INCREMENT, @\\
\mbox{}\verb@    counters::PRE_INCREMENT, @\\
\mbox{}\verb@    counters::POST_DECREMENT, counters::PRE_DECREMENT, @\\
\mbox{}\verb@    counters::UNARY_PLUS, counters::UNARY_MINUS, @\\
\mbox{}\verb@    counters::PLUS, counters::MINUS, counters::TIMES, @\\
\mbox{}\verb@    counters::DIVIDE, counters::MODULO,@\\
\mbox{}\verb@    counters::LEFT_SHIFT, counters::RIGHT_SHIFT,@\\
\mbox{}\verb@    counters::PLUS_ASSIGN, counters::MINUS_ASSIGN, @\\
\mbox{}\verb@    counters::TIMES_ASSIGN, counters::DIVIDE_ASSIGN, @\\
\mbox{}\verb@    counters::MODULO_ASSIGN,@\\
\mbox{}\verb@    counters::LEFT_SHIFT_ASSIGN, counters::RIGHT_SHIFT_ASSIGN,@\\
\mbox{}\verb@    counters::DEREFERENCE, counters::MEMBER, @\\
\mbox{}\verb@    counters::SUBSCRIPT, counters::FUNCTION_CALL,@\\
\mbox{}\verb@    counters::NEGATE, counters::AND, counters::AND_ASSIGN, @\\
\mbox{}\verb@    counters::OR, counters::OR_ASSIGN, counters::XOR, @\\
\mbox{}\verb@    counters::XOR_ASSIGN,@\\
\mbox{}\verb@  };@\\
\mbox{}\verb@  counters::operator_type group3[] = { @\\
\mbox{}\verb@    counters::BASE, @\\
\mbox{}\verb@    counters::DTOR, @\\
\mbox{}\verb@    counters::GENERATION, @\\
\mbox{}\verb@  };@\\
\mbox{}\verb@  //  counters::scale_recorder_visitor<@\\
\mbox{}\verb@  //    counters::group_recorder_visitor<> > my_visitor(0.001);@\\
\mbox{}\verb@  counters::group_recorder_visitor<> my_visitor;@\\
\mbox{}\verb@  my_visitor.add("Compare", group0, @\\
\mbox{}\verb@              group0 + sizeof(group0) / sizeof(group0[0]));@\\
\mbox{}\verb@  my_visitor.add("Assign", group1, @\\
\mbox{}\verb@              group1 + sizeof(group1) / sizeof(group1[0]));@\\
\mbox{}\verb@  my_visitor.add("Other", group2, @\\
\mbox{}\verb@              group2 + sizeof(group2) / sizeof(group2[0]));@\\
\mbox{}\verb@  my_visitor.hide(group3, @\\
\mbox{}\verb@               group3 + sizeof(group3) / sizeof(group3[0]));@\\
\mbox{}\verb@@\\
\mbox{}\verb@  unsigned long N, N1, N2;@\\
\mbox{}\verb@  unsigned int reps;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  N1 = 1;@\\
\mbox{}\verb@  N2 = 1048576;@\\
\mbox{}\verb@  reps = 1;@\\
\mbox{}\verb@  recorder<> my_recorder;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  for (N = N1; N <= N2; N *= 2)@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      my_recorder.pause();@\\
\mbox{}\verb@      cout<<N<<endl;@\\
\mbox{}\verb@      @\\
\mbox{}\verb@      for (int i = 0; i < (N/2); ++i) {@\\
\mbox{}\verb@  r->add_destination(test1048576);@\\
\mbox{}\verb@      }@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@    //////////////////////////////  @\\
\mbox{}\verb@      // Baseline Operations Here @\\
\mbox{}\verb@    out1.clear();@\\
\mbox{}\verb@    defaultItems.clear();@\\
\mbox{}\verb@           @\\
\mbox{}\verb@    // End of Baseline Operations@\\
\mbox{}\verb@    ///////////////////////////////@\\
\mbox{}\verb@    // Main Timed Operation@\\
\mbox{}\verb@    my_recorder.resume();@\\
\mbox{}\verb@    r->distribute(citer(v.begin()),citer( v.end()));@\\
\mbox{}\verb@    //////////////////////////////////////@\\
\mbox{}\verb@    my_recorder.record();@\\
\mbox{}\verb@    my_recorder.report(cout,my_visitor);@\\
\mbox{}\verb@    my_recorder.clear();@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@\\
\mbox{}\verb@int main()@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  test2();  @\\
\mbox{}\verb@  return 0;@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@
\end{list}
\vspace{-2ex}
\end{flushleft}
\section{Test 3}
\label{sec-code-count-3}
\begin{flushleft} \small \label{part105}
\verb@"opcount_test3.cpp"@ {\footnotesize \hypertarget{190}{190} }$\equiv$
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@#include <cmath>@\\
\mbox{}\verb@#include <cstdlib>@\\
\mbox{}\verb@#include <ctime>@\\
\mbox{}\verb@#include <iostream>@\\
\mbox{}\verb@#include <vector>@\\
\mbox{}\verb@#include <algorithm>@\\
\mbox{}\verb@#include <iostream>@\\
\mbox{}\verb@#include <vector>@\\
\mbox{}\verb@#include <list>@\\
\mbox{}\verb@#include <iterator>@\\
\mbox{}\verb@#include "timer.h"@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@#define DEFAULT_COUNTER_TYPE int@\\
\mbox{}\verb@#include "counters.h"@\\
\mbox{}\verb@@\\
\mbox{}\verb@#include "router.hpp"@\\
\mbox{}\verb@@\\
\mbox{}\verb@using namespace std;@\\
\mbox{}\verb@using std::cout;@\\
\mbox{}\verb@using std::endl;@\\
\mbox{}\verb@using std::vector;@\\
\mbox{}\verb@using std::list;@\\
\mbox{}\verb@using std::back_inserter;@\\
\mbox{}\verb@using std::ostream_iterator;@\\
\mbox{}\verb@using std::back_insert_iterator;@\\
\mbox{}\verb@@\\
\mbox{}\verb@using namespace counters;@\\
\mbox{}\verb@using gdfa::router;@\\
\mbox{}\verb@using gdfa::destination;@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@bool less_than_n(const value_counter<int> & element) {@\\
\mbox{}\verb@      if (element < (value_counter<int>)1048576) {@\\
\mbox{}\verb@        return true;@\\
\mbox{}\verb@      }@\\
\mbox{}\verb@      @\\
\mbox{}\verb@      return false;    @\\
\mbox{}\verb@}@\\
\mbox{}\verb@@\\
\mbox{}\verb@void test() {@\\
\mbox{}\verb@  cout << "Test 3\nSimple Version of Distribute\nTesting N\n";@\\
\mbox{}\verb@  cout<<"Timing distribute on integers." << endl;@\\
\mbox{}\verb@  srand(time(0));@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  typedef counters::iterator_counter<@\\
\mbox{}\verb@   vector<value_counter<int> >::iterator> citer;@\\
\mbox{}\verb@  //typedef the counter vector@\\
\mbox{}\verb@  typedef vector<value_counter<int> > count_vector;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  // Initial Setup@\\
\mbox{}\verb@  count_vector v, out1, defaultItems;@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  typedef std::back_insert_iterator<count_vector> BItype;@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  out1.clear();@\\
\mbox{}\verb@  defaultItems.clear();@\\
\mbox{}\verb@@\\
\mbox{}\verb@  //now we need to print the results@\\
\mbox{}\verb@  /*this code is from quantiles-count.cpp, by DRM,@\\
\mbox{}\verb@  http://www.cs.rpi.edu/~musser/gsd/quantiles/quantiles-count.cpp@\\
\mbox{}\verb@  this code sets up the operations counting and reporting*/@\\
\mbox{}\verb@  counters::operator_type group0[] = { @\\
\mbox{}\verb@    counters::LESS_THAN, counters::EQUALITY@\\
\mbox{}\verb@  };@\\
\mbox{}\verb@  counters::operator_type group1[] = { @\\
\mbox{}\verb@    counters::DEFAULT_CTOR, @\\
\mbox{}\verb@    counters::COPY_CTOR, @\\
\mbox{}\verb@    counters::OTHER_CTOR, @\\
\mbox{}\verb@    counters::ASSIGNMENT,@\\
\mbox{}\verb@  };@\\
\mbox{}\verb@  counters::operator_type group2[] = { @\\
\mbox{}\verb@    counters::CONVERSION, counters::POST_INCREMENT, @\\
\mbox{}\verb@    counters::PRE_INCREMENT, @\\
\mbox{}\verb@    counters::POST_DECREMENT, counters::PRE_DECREMENT, @\\
\mbox{}\verb@    counters::UNARY_PLUS, counters::UNARY_MINUS, @\\
\mbox{}\verb@    counters::PLUS, counters::MINUS, counters::TIMES, @\\
\mbox{}\verb@    counters::DIVIDE, counters::MODULO,@\\
\mbox{}\verb@    counters::LEFT_SHIFT, counters::RIGHT_SHIFT,@\\
\mbox{}\verb@    counters::PLUS_ASSIGN, counters::MINUS_ASSIGN, @\\
\mbox{}\verb@    counters::TIMES_ASSIGN, counters::DIVIDE_ASSIGN, @\\
\mbox{}\verb@    counters::MODULO_ASSIGN,@\\
\mbox{}\verb@    counters::LEFT_SHIFT_ASSIGN, counters::RIGHT_SHIFT_ASSIGN,@\\
\mbox{}\verb@    counters::DEREFERENCE, counters::MEMBER, @\\
\mbox{}\verb@    counters::SUBSCRIPT, counters::FUNCTION_CALL,@\\
\mbox{}\verb@    counters::NEGATE, counters::AND, counters::AND_ASSIGN, @\\
\mbox{}\verb@    counters::OR, counters::OR_ASSIGN, counters::XOR, @\\
\mbox{}\verb@    counters::XOR_ASSIGN,@\\
\mbox{}\verb@  };@\\
\mbox{}\verb@  counters::operator_type group3[] = { @\\
\mbox{}\verb@    counters::BASE, @\\
\mbox{}\verb@    counters::DTOR, @\\
\mbox{}\verb@    counters::GENERATION, @\\
\mbox{}\verb@  };@\\
\mbox{}\verb@  //  counters::scale_recorder_visitor<@\\
\mbox{}\verb@  //    counters::group_recorder_visitor<> > my_visitor(0.001);@\\
\mbox{}\verb@  counters::group_recorder_visitor<> my_visitor;@\\
\mbox{}\verb@  my_visitor.add("Compare", group0, @\\
\mbox{}\verb@     group0 + sizeof(group0) / sizeof(group0[0]));@\\
\mbox{}\verb@  my_visitor.add("Assign", group1, @\\
\mbox{}\verb@     group1 + sizeof(group1) / sizeof(group1[0]));@\\
\mbox{}\verb@  my_visitor.add("Other", group2, @\\
\mbox{}\verb@     group2 + sizeof(group2) / sizeof(group2[0]));@\\
\mbox{}\verb@  my_visitor.hide(group3, @\\
\mbox{}\verb@      group3 + sizeof(group3) / sizeof(group3[0]));@\\
\mbox{}\verb@@\\
\mbox{}\verb@  unsigned long N, N1, N2;@\\
\mbox{}\verb@  unsigned int reps;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  N2 = 1048576;@\\
\mbox{}\verb@  N1 = 1;@\\
\mbox{}\verb@  reps = 1;@\\
\mbox{}\verb@  recorder<> my_recorder;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  for (N = N1; N <= N2; N *= 2)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    my_recorder.pause();@\\
\mbox{}\verb@    cout<<N<<endl;@\\
\mbox{}\verb@    v.clear(); @\\
\mbox{}\verb@    v.reserve(N);@\\
\mbox{}\verb@    for (int i = 0; i < N; ++i) {@\\
\mbox{}\verb@      v.push_back((value_counter<int>)i);@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@@\\
\mbox{}\verb@    //////////////////////////////  @\\
\mbox{}\verb@    // Baseline Operations Here @\\
\mbox{}\verb@    out1.clear();@\\
\mbox{}\verb@    defaultItems.clear();@\\
\mbox{}\verb@    // End of Baseline Operations@\\
\mbox{}\verb@    ///////////////////////////////@\\
\mbox{}\verb@    // Main Timed Operation@\\
\mbox{}\verb@    my_recorder.resume();@\\
\mbox{}\verb@    gdfa::distribute(citer(v.begin()), citer(v.end()),@\\
\mbox{}\verb@     back_inserter(out1), back_inserter(defaultItems),@\\
\mbox{}\verb@     less_than_n);@\\
\mbox{}\verb@    //////////////////////////////////////@\\
\mbox{}\verb@    my_recorder.record();@\\
\mbox{}\verb@    my_recorder.report(cout,my_visitor);@\\
\mbox{}\verb@    my_recorder.clear();@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@\\
\mbox{}\verb@int main()@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  test();  @\\
\mbox{}\verb@  return 0;@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@
\end{list}
\vspace{-2ex}
\end{flushleft}
\section{Test 4}
\label{sec-code-count-4}
\begin{flushleft} \small \label{part106}
\verb@"opcount_test4.cpp"@ {\footnotesize \hypertarget{193}{193} }$\equiv$
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@#include <cmath>@\\
\mbox{}\verb@#include <cstdlib>@\\
\mbox{}\verb@#include <ctime>@\\
\mbox{}\verb@#include <iostream>@\\
\mbox{}\verb@#include <vector>@\\
\mbox{}\verb@#include <algorithm>@\\
\mbox{}\verb@#include <iostream>@\\
\mbox{}\verb@#include <vector>@\\
\mbox{}\verb@#include <list>@\\
\mbox{}\verb@#include <iterator>@\\
\mbox{}\verb@@\\
\mbox{}\verb@#include "timer.h"@\\
\mbox{}\verb@@\\
\mbox{}\verb@#define DEFAULT_COUNTER_TYPE int@\\
\mbox{}\verb@#include "counters.h"@\\
\mbox{}\verb@@\\
\mbox{}\verb@#include "router.hpp"@\\
\mbox{}\verb@@\\
\mbox{}\verb@using namespace std;@\\
\mbox{}\verb@using std::cout;@\\
\mbox{}\verb@using std::endl;@\\
\mbox{}\verb@using std::vector;@\\
\mbox{}\verb@using std::list;@\\
\mbox{}\verb@using std::back_inserter;@\\
\mbox{}\verb@using std::ostream_iterator;@\\
\mbox{}\verb@using std::back_insert_iterator;@\\
\mbox{}\verb@@\\
\mbox{}\verb@using namespace counters;@\\
\mbox{}\verb@using gdfa::router;@\\
\mbox{}\verb@using gdfa::destination;@\\
\mbox{}\verb@@\\
\mbox{}\verb@template <typename OutputIterator>@\\
\mbox{}\verb@class less_than_n : public destination<value_counter<int> >@\\
\mbox{}\verb@{@\\
\mbox{}\verb@private:@\\
\mbox{}\verb@  OutputIterator out;@\\
\mbox{}\verb@  value_counter<int>  n;@\\
\mbox{}\verb@    @\\
\mbox{}\verb@public:@\\
\mbox{}\verb@  less_than_n(OutputIterator _out, int _n) : out(_out), n(_n) {}@\\
\mbox{}\verb@@\\
\mbox{}\verb@  bool distribute(const value_counter<int> & element)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    if (element > n)@\\
\mbox{}\verb@      {@\\
\mbox{}\verb@        *(out++) = element;@\\
\mbox{}\verb@        return true;@\\
\mbox{}\verb@      }@\\
\mbox{}\verb@      @\\
\mbox{}\verb@    return false;    @\\
\mbox{}\verb@  }@\\
\mbox{}\verb@};@\\
\mbox{}\verb@@\\
\mbox{}\verb@template <typename OutputIterator>@\\
\mbox{}\verb@class my_default : public destination<value_counter<int> >@\\
\mbox{}\verb@{@\\
\mbox{}\verb@private:@\\
\mbox{}\verb@  OutputIterator out;@\\
\mbox{}\verb@    @\\
\mbox{}\verb@public:@\\
\mbox{}\verb@  my_default(OutputIterator _out) : out(_out) {}@\\
\mbox{}\verb@    @\\
\mbox{}\verb@  bool distribute(const value_counter<int> & n)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    *(out) = n;@\\
\mbox{}\verb@    return true;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@};@\\
\mbox{}\verb@@\\
\mbox{}\verb@void test4() {@\\
\mbox{}\verb@  cout << "Test 4\nTesting M x N\nTiming distribute on integers.\n";@\\
\mbox{}\verb@  cout<<"Distribute to just 1 of the destinations." << endl;@\\
\mbox{}\verb@  srand(time(0));@\\
\mbox{}\verb@@\\
\mbox{}\verb@  typedef counters::iterator_counter<@\\
\mbox{}\verb@    vector<value_counter<int> >::iterator> citer;@\\
\mbox{}\verb@  //typedef the counter vector@\\
\mbox{}\verb@  typedef vector<value_counter<int> > count_vector;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  // Initial Setup@\\
\mbox{}\verb@  router<value_counter<int> > *r;@\\
\mbox{}\verb@  r = new router<value_counter<int> >;@\\
\mbox{}\verb@  count_vector v, out1, out2, defaultItems;@\\
\mbox{}\verb@ @\\
\mbox{}\verb@  typedef std::back_insert_iterator<count_vector> BItype;@\\
\mbox{}\verb@  delete r;@\\
\mbox{}\verb@  r = new router<value_counter<int> >;@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  out1.clear();@\\
\mbox{}\verb@  out2.clear();@\\
\mbox{}\verb@  defaultItems.clear();@\\
\mbox{}\verb@@\\
\mbox{}\verb@  less_than_n<BItype> test1048576(back_inserter(out1), 1048576);@\\
\mbox{}\verb@  my_default<BItype> defaultTest(back_inserter(defaultItems)); @\\
\mbox{}\verb@  @\\
\mbox{}\verb@  r->set_default(defaultTest);@\\
\mbox{}\verb@@\\
\mbox{}\verb@  counters::operator_type group0[] = { @\\
\mbox{}\verb@    counters::LESS_THAN, counters::EQUALITY@\\
\mbox{}\verb@  };@\\
\mbox{}\verb@  counters::operator_type group1[] = { @\\
\mbox{}\verb@    counters::DEFAULT_CTOR, @\\
\mbox{}\verb@    counters::COPY_CTOR, @\\
\mbox{}\verb@    counters::OTHER_CTOR, @\\
\mbox{}\verb@    counters::ASSIGNMENT,@\\
\mbox{}\verb@  };@\\
\mbox{}\verb@  counters::operator_type group2[] = { @\\
\mbox{}\verb@    counters::CONVERSION, counters::POST_INCREMENT, @\\
\mbox{}\verb@    counters::PRE_INCREMENT, @\\
\mbox{}\verb@    counters::POST_DECREMENT, counters::PRE_DECREMENT, @\\
\mbox{}\verb@    counters::UNARY_PLUS, counters::UNARY_MINUS, @\\
\mbox{}\verb@    counters::PLUS, counters::MINUS, counters::TIMES, @\\
\mbox{}\verb@    counters::DIVIDE, counters::MODULO,@\\
\mbox{}\verb@    counters::LEFT_SHIFT, counters::RIGHT_SHIFT,@\\
\mbox{}\verb@    counters::PLUS_ASSIGN, counters::MINUS_ASSIGN, @\\
\mbox{}\verb@    counters::TIMES_ASSIGN, counters::DIVIDE_ASSIGN, @\\
\mbox{}\verb@    counters::MODULO_ASSIGN,@\\
\mbox{}\verb@    counters::LEFT_SHIFT_ASSIGN, counters::RIGHT_SHIFT_ASSIGN,@\\
\mbox{}\verb@    counters::DEREFERENCE, counters::MEMBER, @\\
\mbox{}\verb@    counters::SUBSCRIPT, counters::FUNCTION_CALL,@\\
\mbox{}\verb@    counters::NEGATE, counters::AND, counters::AND_ASSIGN, @\\
\mbox{}\verb@    counters::OR, counters::OR_ASSIGN, counters::XOR, @\\
\mbox{}\verb@    counters::XOR_ASSIGN,@\\
\mbox{}\verb@  };@\\
\mbox{}\verb@  counters::operator_type group3[] = { @\\
\mbox{}\verb@    counters::BASE, @\\
\mbox{}\verb@    counters::DTOR, @\\
\mbox{}\verb@    counters::GENERATION, @\\
\mbox{}\verb@  };@\\
\mbox{}\verb@@\\
\mbox{}\verb@  counters::group_recorder_visitor<> my_visitor;@\\
\mbox{}\verb@  my_visitor.add("Compare", group0, @\\
\mbox{}\verb@                 group0 + sizeof(group0) / sizeof(group0[0]));@\\
\mbox{}\verb@  my_visitor.add("Assign", group1, @\\
\mbox{}\verb@                 group1 + sizeof(group1) / sizeof(group1[0]));@\\
\mbox{}\verb@  my_visitor.add("Other", group2, @\\
\mbox{}\verb@                 group2 + sizeof(group2) / sizeof(group2[0]));@\\
\mbox{}\verb@  my_visitor.hide(group3, @\\
\mbox{}\verb@                  group3 + sizeof(group3) / sizeof(group3[0]));@\\
\mbox{}\verb@@\\
\mbox{}\verb@  unsigned long N, N1, N2;@\\
\mbox{}\verb@  unsigned int reps;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  N1 = 1;@\\
\mbox{}\verb@  N2 = 16384;@\\
\mbox{}\verb@  reps = 1;@\\
\mbox{}\verb@  recorder<> my_recorder;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  for (N = N1; N <= N2; N *= 2)@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      my_recorder.pause();@\\
\mbox{}\verb@      cout<<"\nM = "<<N<<endl@\\
\mbox{}\verb@          <<"***************************************\n"@\\
\mbox{}\verb@          <<"***************************************\n";@\\
\mbox{}\verb@          @\\
\mbox{}\verb@      for (int i = 0; i < (N/2); ++i) {@\\
\mbox{}\verb@        r->add_destination(test1048576);@\\
\mbox{}\verb@      }@\\
\mbox{}\verb@@\\
\mbox{}\verb@      for (int realN = N1; realN <= N2; realN *= 2)@\\
\mbox{}\verb@        {@\\
\mbox{}\verb@          my_recorder.pause();@\\
\mbox{}\verb@          cout<<"N = "<<realN<<endl@\\
\mbox{}\verb@              <<"***************************************\n";@\\
\mbox{}\verb@@\\
\mbox{}\verb@          v.clear(); @\\
\mbox{}\verb@          v.reserve(realN);@\\
\mbox{}\verb@          for (int i = 0; i < realN; ++i)@\\
\mbox{}\verb@            {@\\
\mbox{}\verb@              v.push_back((value_counter<int>)i);@\\
\mbox{}\verb@            }@\\
\mbox{}\verb@          out1.clear();@\\
\mbox{}\verb@          defaultItems.clear();@\\
\mbox{}\verb@@\\
\mbox{}\verb@           @\\
\mbox{}\verb@          my_recorder.resume();@\\
\mbox{}\verb@          r->distribute(citer(v.begin()),citer( v.end()));@\\
\mbox{}\verb@          my_recorder.record();@\\
\mbox{}\verb@          my_recorder.report(cout,my_visitor);@\\
\mbox{}\verb@          my_recorder.clear();@\\
\mbox{}\verb@        }@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@\\
\mbox{}\verb@int main()@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  test4();  @\\
\mbox{}\verb@  return 0;@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@
\end{list}
\vspace{-2ex}
\end{flushleft}
\chapter{Code for Correctness Tests}
\label{sec-code-correctness}
\section{Common Validation Methods}
\label{sec-code-validate-common}
\begin{flushleft} \small \label{part107}
\verb@"validate.hpp"@ {\footnotesize \hypertarget{198}{198} }$\equiv$
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@//validate.h version 1.0@\\
\mbox{}\verb@#ifndef _VALIDATE_H@\\
\mbox{}\verb@#define _VALIDATE_H@\\
\mbox{}\verb@@\\
\mbox{}\verb@#include <vector>@\\
\mbox{}\verb@#include <iostream>@\\
\mbox{}\verb@#include <list>@\\
\mbox{}\verb@#include <deque>@\\
\mbox{}\verb@using std::list;@\\
\mbox{}\verb@using std::deque;@\\
\mbox{}\verb@using std::vector;@\\
\mbox{}\verb@using std::cout;@\\
\mbox{}\verb@using std::endl;@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\hbox{\colorbox{light}{$\langle$first validate function {\footnotesize \hyperlink{199}{199}}$\rangle$}}\verb@@\\
\mbox{}\verb@@\hbox{\colorbox{light}{$\langle$second validate function {\footnotesize \hyperlink{200a}{200a}}$\rangle$}}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@#endif@\\
\mbox{}\verb@@
\end{list}
\vspace{-2ex}
\end{flushleft}
\subsection {First Validate Function}
\label{sec-code-validate-first}
This validate function iterates through the results of filtering the 
same data but using either different priorities, storage types,  etc. 
Because of the nature of the input, the results should always be the 
same.

\begin{flushleft} \small
\begin{minipage}{\linewidth}\color{blue} \label{part108}
\colorbox{light}{$\langle$first validate function {\footnotesize \hypertarget{199}{199}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@template<typename conttype1,typename conttype2>@\\
\mbox{}\verb@bool validate(conttype1 key[],conttype2 res[],int size,@\\
\mbox{}\verb@              bool rev = false)@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  typedef typename conttype1::iterator key_iter;@\\
\mbox{}\verb@  key_iter ikey;@\\
\mbox{}\verb@  typedef typename conttype2::iterator res_iter;@\\
\mbox{}\verb@  res_iter ires;@\\
\mbox{}\verb@  for(int i = 0;i < size;i++)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    if(rev)@\\
\mbox{}\verb@      reverse(res[i].begin(),res[i].end());@\\
\mbox{}\verb@@\\
\mbox{}\verb@    ikey = key[i].begin();@\\
\mbox{}\verb@    ires = res[i].begin();@\\
\mbox{}\verb@    while(ikey != key[i].end() && ires != res[i].end())@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      if(*ikey != *ires)@\\
\mbox{}\verb@      {@\\
\mbox{}\verb@        cout<<"In container "<<i<<" "<<*ires<<" != "<<*ikey<<endl;@\\
\mbox{}\verb@        return false;@\\
\mbox{}\verb@      }@\\
\mbox{}\verb@      ikey++;@\\
\mbox{}\verb@      ires++;@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@    if(ikey!=key[i].end())@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      cout<<"Not enough elements in container "<<i<<endl;@\\
\mbox{}\verb@      return false;@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@    if(ires!=res[i].end())@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      cout<<"Too many elements in container "<<i<<endl;@\\
\mbox{}\verb@      return false;@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  return true;@\\
\mbox{}\verb@}@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Used in part \hyperlink{198}{198}.
\end{list}
\end{minipage}\\[4ex]
\end{flushleft}
\subsection{Second Validate Function}
\label{sec-code-validate-second}
\begin{flushleft} \small
\begin{minipage}{\linewidth}\color{blue} \label{part109}
\colorbox{light}{$\langle$second validate function {\footnotesize \hypertarget{200a}{200a}}$\rangle\equiv$}
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@template<typename conttype1,typename conttype2>@\\
\mbox{}\verb@bool validatesize(conttype1 key[],conttype2 res[],int size)@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  typedef typename conttype1::iterator key_iter;@\\
\mbox{}\verb@  key_iter ikey;@\\
\mbox{}\verb@  typedef typename conttype2::iterator res_iter;@\\
\mbox{}\verb@  res_iter ires;@\\
\mbox{}\verb@  for(int i = 0;i < size;i++)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    if(key[i].size() != res[i].size())@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      cout<<"match failed for container: "<<i<<endl;@\\
\mbox{}\verb@      return false;@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  return true;@\\
\mbox{}\verb@}@
\end{list}
\vspace{-1ex}
\footnotesize\addtolength{\baselineskip}{-1ex}
\begin{list}{}{\setlength{\itemsep}{-\parsep}\setlength{\itemindent}{-\leftmargin}}
\item Used in part \hyperlink{198}{198}.
\end{list}
\end{minipage}\\[4ex]
\end{flushleft}
\section{Helper Classes}
\subsection{Test Classes}
\label{sec-code-test_classes.hpp}
\begin{flushleft} \small \label{part110}
\verb@"test_classes.hpp"@ {\footnotesize \hypertarget{200b}{200b} }$\equiv$
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@//test_classes.h version 1.3@\\
\mbox{}\verb@#ifndef TEST_CLASSES_H@\\
\mbox{}\verb@#define TEST_CLASSES_H@\\
\mbox{}\verb@@\\
\mbox{}\verb@#include <vector>@\\
\mbox{}\verb@#include <iostream>@\\
\mbox{}\verb@#include "router.hpp"@\\
\mbox{}\verb@#include <ctype.h>@\\
\mbox{}\verb@#include <map>@\\
\mbox{}\verb@using std::pair;@\\
\mbox{}\verb@using std::string;@\\
\mbox{}\verb@using std::vector;@\\
\mbox{}\verb@using std::cout;@\\
\mbox{}\verb@using std::endl;@\\
\mbox{}\verb@using gdfa::router;@\\
\mbox{}\verb@using gdfa::destination;@\\
\mbox{}\verb@@\\
\mbox{}\verb@/* word_sorter sorts strings based on their first letter.  if @\\
\mbox{}\verb@the first letter of the string matches m_first_letter the class @\\
\mbox{}\verb@will write the string its output_iterator. this class is case @\\
\mbox{}\verb@insensitive meaning that if m_first_letter is 'a' words @\\
\mbox{}\verb@beginning with 'A' or 'a' will be filtered.  Also note that when @\\
\mbox{}\verb@an object of this class is first created that it will convert @\\
\mbox{}\verb@the char given to a lower case letter so that it operates @\\
\mbox{}\verb@correctly. */@\\
\mbox{}\verb@template<typename output_iterator>@\\
\mbox{}\verb@class word_sorter : public destination<string>@\\
\mbox{}\verb@{@\\
\mbox{}\verb@   private:@\\
\mbox{}\verb@  output_iterator m_out;@\\
\mbox{}\verb@  char m_first_letter;@\\
\mbox{}\verb@  @\\
\mbox{}\verb@   public:@\\
\mbox{}\verb@  word_sorter(output_iterator out, char first_letter)@\\
\mbox{}\verb@         : m_out(out) { m_first_letter =@\\
\mbox{}\verb@                       tolower((const int)first_letter);}@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  /*out distribute function checks the first letter to see if it is@\\
\mbox{}\verb@  the same as in the predicate*/@\\
\mbox{}\verb@  bool distribute(const string& element)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@     if (tolower((const int)element[0]) == m_first_letter)@\\
\mbox{}\verb@     {@\\
\mbox{}\verb@    *m_out++ = element;@\\
\mbox{}\verb@    return true;@\\
\mbox{}\verb@     }@\\
\mbox{}\verb@     @\\
\mbox{}\verb@     return false;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@};@\\
\mbox{}\verb@@\\
\mbox{}\verb@/*length_counter filters on the length of the input string.  if the@\\
\mbox{}\verb@string is of length m_length the object will write the string to@\\
\mbox{}\verb@its output_iterator*/@\\
\mbox{}\verb@template<typename output_iterator>@\\
\mbox{}\verb@class length_counter : public destination<string>@\\
\mbox{}\verb@{@\\
\mbox{}\verb@   private:@\\
\mbox{}\verb@  output_iterator m_out;@\\
\mbox{}\verb@  int m_length;@\\
\mbox{}\verb@  @\\
\mbox{}\verb@   public:@\\
\mbox{}\verb@  length_counter(output_iterator out, int length)@\\
\mbox{}\verb@         : m_out(out), m_length(length) {}@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  /*out distribute function checks the first letter to see if it is@\\
\mbox{}\verb@  the same as in the predicate*/@\\
\mbox{}\verb@  bool distribute(const string& element)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@     if(element.size() == m_length)@\\
\mbox{}\verb@     {@\\
\mbox{}\verb@    *m_out++ = element;@\\
\mbox{}\verb@    return true;@\\
\mbox{}\verb@     }@\\
\mbox{}\verb@     @\\
\mbox{}\verb@     return false;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@@\\
\mbox{}\verb@};@\\
\mbox{}\verb@@\\
\mbox{}\verb@/*contains letter checks to see is the input string contains the @\\
\mbox{}\verb@char m_letter. if it does the object will write the string to @\\
\mbox{}\verb@its output_iterator.  this letter is case sensitive, meaning @\\
\mbox{}\verb@that if a lowercase 'a' is given that words with 'A' will not be @\\
\mbox{}\verb@filtered unless they also have an 'a'*/@\\
\mbox{}\verb@template<typename output_iterator>@\\
\mbox{}\verb@class contains_letter : public destination<string>@\\
\mbox{}\verb@{@\\
\mbox{}\verb@private:@\\
\mbox{}\verb@        output_iterator m_out;@\\
\mbox{}\verb@        char m_letter;@\\
\mbox{}\verb@public:@\\
\mbox{}\verb@        contains_letter(output_iterator out,const char letter)@\\
\mbox{}\verb@                        : m_out(out), m_letter(letter) {}@\\
\mbox{}\verb@        bool distribute(const string &n)@\\
\mbox{}\verb@        {@\\
\mbox{}\verb@                if(n.find(m_letter) < n.size())@\\
\mbox{}\verb@                {@\\
\mbox{}\verb@                        *m_out++ = n;@\\
\mbox{}\verb@                        return true;@\\
\mbox{}\verb@                }@\\
\mbox{}\verb@                return false;@\\
\mbox{}\verb@        }@\\
\mbox{}\verb@};@\\
\mbox{}\verb@@\\
\mbox{}\verb@/*the default class is used to catch anything that is not@\\
\mbox{}\verb@filtered*/@\\
\mbox{}\verb@template<typename output_iterator>@\\
\mbox{}\verb@class my_default : public destination<string>@\\
\mbox{}\verb@{@\\
\mbox{}\verb@   private:@\\
\mbox{}\verb@  output_iterator m_out;@\\
\mbox{}\verb@   public:@\\
\mbox{}\verb@  my_default(output_iterator out)@\\
\mbox{}\verb@         : m_out(out) {}@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  bool distribute(const string& n)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@     *m_out++ = n;@\\
\mbox{}\verb@     return true;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@};@\\
\mbox{}\verb@@\\
\mbox{}\verb@/*a specialization of word_sorter that works with pairs. needed@\\
\mbox{}\verb@for filtering from a map*/@\\
\mbox{}\verb@template<typename output_iterator>@\\
\mbox{}\verb@class word_sortermap : public destination<pair<string,int> >@\\
\mbox{}\verb@{@\\
\mbox{}\verb@   private:@\\
\mbox{}\verb@  output_iterator m_out;@\\
\mbox{}\verb@  char m_first_letter;@\\
\mbox{}\verb@  @\\
\mbox{}\verb@   public:@\\
\mbox{}\verb@  word_sortermap(output_iterator out, char first_letter)@\\
\mbox{}\verb@         : m_out(out) { m_first_letter =@\\
\mbox{}\verb@                       tolower((const int)first_letter);}@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  /*out distribute function checks the first letter to see if it is@\\
\mbox{}\verb@  the same as in the predicate*/@\\
\mbox{}\verb@  bool distribute(const pair<string,int>& element)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@     if (tolower((const int)element.first[0]) == m_first_letter)@\\
\mbox{}\verb@     {@\\
\mbox{}\verb@    *m_out++ = element;@\\
\mbox{}\verb@    return true;@\\
\mbox{}\verb@     }@\\
\mbox{}\verb@     @\\
\mbox{}\verb@     return false;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@};@\\
\mbox{}\verb@@\\
\mbox{}\verb@/*contains string works much like contains letter, except that it@\\
\mbox{}\verb@checks to see if the input contains a substring*/@\\
\mbox{}\verb@template<typename output_iterator>@\\
\mbox{}\verb@class contains_string : public destination<string>@\\
\mbox{}\verb@{@\\
\mbox{}\verb@private:@\\
\mbox{}\verb@        output_iterator m_out;@\\
\mbox{}\verb@        string m_str;@\\
\mbox{}\verb@public:@\\
\mbox{}\verb@        contains_string(output_iterator out,string str)@\\
\mbox{}\verb@                        : m_out(out), m_str(str) {}@\\
\mbox{}\verb@        bool distribute(const string &n)@\\
\mbox{}\verb@        {@\\
\mbox{}\verb@                if(n.find(m_str) < n.size())@\\
\mbox{}\verb@                {@\\
\mbox{}\verb@                        *m_out++ = n;@\\
\mbox{}\verb@                        return true;@\\
\mbox{}\verb@                }@\\
\mbox{}\verb@                return false;@\\
\mbox{}\verb@        }@\\
\mbox{}\verb@};@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@/*a specialization of my_default that works with pairs.  needed for@\\
\mbox{}\verb@filtering from a map*/@\\
\mbox{}\verb@template<typename output_iterator>@\\
\mbox{}\verb@class my_defaultmap : public destination<pair<string,int> >@\\
\mbox{}\verb@{@\\
\mbox{}\verb@   private:@\\
\mbox{}\verb@  output_iterator m_out;@\\
\mbox{}\verb@   public:@\\
\mbox{}\verb@  my_defaultmap(output_iterator out)@\\
\mbox{}\verb@         : m_out(out) {}@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  bool distribute(const pair<string,int>& n)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@     *m_out++ = n;@\\
\mbox{}\verb@     return true;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@};@\\
\mbox{}\verb@@\\
\mbox{}\verb@void createinputstring(vector<string> &storage)@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  for(int i = 0;i<27;i++)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    for(int j = 0;j < 27;j++)@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      for(int k = 0;k<27;k++)@\\
\mbox{}\verb@      {@\\
\mbox{}\verb@        string foo;@\\
\mbox{}\verb@        foo += (char)(i + 97);@\\
\mbox{}\verb@        storage.push_back(foo);@\\
\mbox{}\verb@        foo += (char)(j + 97);@\\
\mbox{}\verb@        storage.push_back(foo);@\\
\mbox{}\verb@        foo += (char)(k + 97);@\\
\mbox{}\verb@        storage.push_back(foo);@\\
\mbox{}\verb@      }@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  random_shuffle(storage.begin(),storage.end());@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@\\
\mbox{}\verb@#endif@\\
\mbox{}\verb@@
\end{list}
\vspace{-2ex}
\end{flushleft}
\subsection{Test Classes}
\label{sec-code-test_classes_fallthrough.hpp}
\begin{flushleft} \small \label{part111}
\verb@"test_classes_fallthrough.hpp"@ {\footnotesize \hypertarget{204}{204} }$\equiv$
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@//test_classes_fallthrough.h version 1.2@\\
\mbox{}\verb@//descriptions of the classes appear before their declaration@\\
\mbox{}\verb@/* all classes in this file do fall through, meaning that it always@\\
\mbox{}\verb@tells the router to keep attempting to filter the input*/@\\
\mbox{}\verb@#ifndef TEST_CLASSES_H@\\
\mbox{}\verb@#define TEST_CLASSES_H@\\
\mbox{}\verb@@\\
\mbox{}\verb@#include <vector>@\\
\mbox{}\verb@#include <iostream>@\\
\mbox{}\verb@#include "router.hpp"@\\
\mbox{}\verb@#include <ctype.h>@\\
\mbox{}\verb@using std::string;@\\
\mbox{}\verb@using std::vector;@\\
\mbox{}\verb@using std::cout;@\\
\mbox{}\verb@using std::endl;@\\
\mbox{}\verb@using gdfa::router;@\\
\mbox{}\verb@using gdfa::destination;@\\
\mbox{}\verb@@\\
\mbox{}\verb@/* word_sorter sorts strings based on their first letter.  if @\\
\mbox{}\verb@the first letter of the string matches m_first_letter the class @\\
\mbox{}\verb@will write the string its output_iterator. this class is case @\\
\mbox{}\verb@insensitive meaning that if m_first_letter is 'a' words @\\
\mbox{}\verb@beginning with 'A' or 'a' will be filtered.  Also note that when @\\
\mbox{}\verb@an object of this class is first created that it will convert @\\
\mbox{}\verb@the char given to a lower case letter so that it operates @\\
\mbox{}\verb@correctly. */@\\
\mbox{}\verb@template<typename output_iterator>@\\
\mbox{}\verb@class word_sorter : public destination<string>@\\
\mbox{}\verb@{@\\
\mbox{}\verb@   private:@\\
\mbox{}\verb@  output_iterator m_out;@\\
\mbox{}\verb@  char m_first_letter;@\\
\mbox{}\verb@  @\\
\mbox{}\verb@   public:@\\
\mbox{}\verb@  word_sorter(output_iterator out, char first_letter)@\\
\mbox{}\verb@  :m_out(out)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    m_first_letter = tolower((const int)first_letter);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  /*out distribute function checks the first letter to see if it is@\\
\mbox{}\verb@  the same as in the predicate*/@\\
\mbox{}\verb@  bool distribute(const string& element)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@     if (tolower((const int)element[0]) == m_first_letter)@\\
\mbox{}\verb@     {@\\
\mbox{}\verb@    *m_out++ = element;@\\
\mbox{}\verb@     }@\\
\mbox{}\verb@     @\\
\mbox{}\verb@     return false;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@};@\\
\mbox{}\verb@@\\
\mbox{}\verb@/*length_counter filters on the length of the input string.  if the@\\
\mbox{}\verb@string is of length m_length the object will write the string to@\\
\mbox{}\verb@its output_iterator*/@\\
\mbox{}\verb@template<typename output_iterator>@\\
\mbox{}\verb@class length_counter : public destination<string>@\\
\mbox{}\verb@{@\\
\mbox{}\verb@   private:@\\
\mbox{}\verb@  output_iterator m_out;@\\
\mbox{}\verb@  int m_length;@\\
\mbox{}\verb@  @\\
\mbox{}\verb@   public:@\\
\mbox{}\verb@  length_counter(output_iterator out, int length)@\\
\mbox{}\verb@         : m_out(out), m_length(length) {}@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  /*out distribute function checks the first letter to see if it is@\\
\mbox{}\verb@  the same as in the predicate*/@\\
\mbox{}\verb@  bool distribute(const string& element)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@     if(element.size() == m_length)@\\
\mbox{}\verb@     {@\\
\mbox{}\verb@    *m_out++ = element;@\\
\mbox{}\verb@     }@\\
\mbox{}\verb@     @\\
\mbox{}\verb@     return false;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@@\\
\mbox{}\verb@};@\\
\mbox{}\verb@@\\
\mbox{}\verb@/*contains letter checks to see is the input string contains the @\\
\mbox{}\verb@char m_letter. if it does the object will write the string to @\\
\mbox{}\verb@its output_iterator.  this letter is case sensitive, meaning @\\
\mbox{}\verb@that if a lowercase 'a' is given that words with 'A' will not be @\\
\mbox{}\verb@filtered unless they also have an 'a'*/@\\
\mbox{}\verb@template<typename output_iterator>@\\
\mbox{}\verb@class contains_letter : public destination<string>@\\
\mbox{}\verb@{@\\
\mbox{}\verb@private:@\\
\mbox{}\verb@        output_iterator m_out;@\\
\mbox{}\verb@        char m_letter;@\\
\mbox{}\verb@public:@\\
\mbox{}\verb@        contains_letter(output_iterator out,const char letter)@\\
\mbox{}\verb@                        : m_out(out), m_letter(letter) {}@\\
\mbox{}\verb@        bool distribute(const string &n)@\\
\mbox{}\verb@        {@\\
\mbox{}\verb@                if(n.find(m_letter) < n.size())@\\
\mbox{}\verb@                {@\\
\mbox{}\verb@                        *m_out++ = n;@\\
\mbox{}\verb@                }@\\
\mbox{}\verb@                return false;@\\
\mbox{}\verb@        }@\\
\mbox{}\verb@};@\\
\mbox{}\verb@@\\
\mbox{}\verb@/*contains string works much like contains letter, except that it@\\
\mbox{}\verb@checks to see if the input contains a substring*/@\\
\mbox{}\verb@template<typename output_iterator>@\\
\mbox{}\verb@class contains_string : public destination<string>@\\
\mbox{}\verb@{@\\
\mbox{}\verb@private:@\\
\mbox{}\verb@        output_iterator m_out;@\\
\mbox{}\verb@        string m_str;@\\
\mbox{}\verb@public:@\\
\mbox{}\verb@        contains_string(output_iterator out,string str)@\\
\mbox{}\verb@                        : m_out(out), m_str(str) {}@\\
\mbox{}\verb@        bool distribute(const string &n)@\\
\mbox{}\verb@        {@\\
\mbox{}\verb@                if(n.find(m_str) < n.size())@\\
\mbox{}\verb@                {@\\
\mbox{}\verb@                        *m_out++ = n;@\\
\mbox{}\verb@                }@\\
\mbox{}\verb@                return false;@\\
\mbox{}\verb@        }@\\
\mbox{}\verb@};@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@/*the default class is used to catch anything that is not@\\
\mbox{}\verb@filtered*/@\\
\mbox{}\verb@template<typename output_iterator>@\\
\mbox{}\verb@class my_default : public destination<string>@\\
\mbox{}\verb@{@\\
\mbox{}\verb@   private:@\\
\mbox{}\verb@  output_iterator m_out;@\\
\mbox{}\verb@   public:@\\
\mbox{}\verb@  my_default(output_iterator out)@\\
\mbox{}\verb@         : m_out(out) {}@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  bool distribute(const string& n)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@     *m_out++ = n;@\\
\mbox{}\verb@     return true;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@};@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@void createinputstring(vector<string> &storage)@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  for(int i = 0;i<27;i++)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    for(int j = 0;j < 27;j++)@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      for(int k = 0;k<27;k++)@\\
\mbox{}\verb@      {@\\
\mbox{}\verb@        string foo;@\\
\mbox{}\verb@        foo += (char)(i + 97);@\\
\mbox{}\verb@        storage.push_back(foo);@\\
\mbox{}\verb@        foo += (char)(j + 97);@\\
\mbox{}\verb@        storage.push_back(foo);@\\
\mbox{}\verb@        foo += (char)(k + 97);@\\
\mbox{}\verb@        storage.push_back(foo);@\\
\mbox{}\verb@      }@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  random_shuffle(storage.begin(),storage.end());@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@\\
\mbox{}\verb@#endif@\\
\mbox{}\verb@@
\end{list}
\vspace{-2ex}
\end{flushleft}
\section{Tests On Built-In Types}
\subsection{Testing with \code{char}s}
\label{sec-code-test-char}
\begin{flushleft} \small \label{part112}
\verb@"test_char.cpp"@ {\footnotesize \hypertarget{208}{208} }$\equiv$
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@//test_char.cpp version 1.0@\\
\mbox{}\verb@#include <iostream>@\\
\mbox{}\verb@#include <fstream>@\\
\mbox{}\verb@#include <string>@\\
\mbox{}\verb@#include <ctype.h>@\\
\mbox{}\verb@#include "router.hpp"@\\
\mbox{}\verb@using std::cout;@\\
\mbox{}\verb@using std::endl;@\\
\mbox{}\verb@using std::vector;@\\
\mbox{}\verb@using std::back_inserter;@\\
\mbox{}\verb@using std::istream_iterator;@\\
\mbox{}\verb@using std::back_insert_iterator;@\\
\mbox{}\verb@using std::string;@\\
\mbox{}\verb@using std::cin;@\\
\mbox{}\verb@@\\
\mbox{}\verb@using gdfa::router;@\\
\mbox{}\verb@using gdfa::destination;@\\
\mbox{}\verb@@\\
\mbox{}\verb@void createinput(vector<char> &storage);@\\
\mbox{}\verb@bool validate(vector<char> sorted[]);@\\
\mbox{}\verb@@\\
\mbox{}\verb@template<typename output_iterator>@\\
\mbox{}\verb@class word_sorter : public destination<char>@\\
\mbox{}\verb@{@\\
\mbox{}\verb@   private:@\\
\mbox{}\verb@  output_iterator m_out;@\\
\mbox{}\verb@  char m_first_letter;@\\
\mbox{}\verb@  @\\
\mbox{}\verb@   public:@\\
\mbox{}\verb@  word_sorter(output_iterator out, char first_letter)@\\
\mbox{}\verb@         : m_out(out), m_first_letter(first_letter) {}@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  /*out distribute function checks the first letter to see if it is@\\
\mbox{}\verb@  the same as in the predicate*/@\\
\mbox{}\verb@  bool distribute(const char& element)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@     if (tolower((const int)element) == m_first_letter)@\\
\mbox{}\verb@     {@\\
\mbox{}\verb@    *m_out++ = element;@\\
\mbox{}\verb@    return true;@\\
\mbox{}\verb@     }@\\
\mbox{}\verb@     @\\
\mbox{}\verb@     return false;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@};@\\
\mbox{}\verb@@\\
\mbox{}\verb@template<typename output_iterator>@\\
\mbox{}\verb@class my_default : public destination<char>@\\
\mbox{}\verb@{@\\
\mbox{}\verb@   private:@\\
\mbox{}\verb@  output_iterator m_out;@\\
\mbox{}\verb@   public:@\\
\mbox{}\verb@  my_default(output_iterator out)@\\
\mbox{}\verb@         : m_out(out) {}@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  bool distribute(const char& n)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@     *m_out++ = n;@\\
\mbox{}\verb@     return true;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@};@\\
\mbox{}\verb@@\\
\mbox{}\verb@int main(int argc,char *argv[])@\\
\mbox{}\verb@{   @\\
\mbox{}\verb@  cout << "\n\n\nTest:  test_char.cpp" @\\
\mbox{}\verb@    << "\n\nTest Using type char as input.\n" @\\
\mbox{}\verb@    << "***********************************\n\n" @\\
\mbox{}\verb@    << "Results:\n\n"; @\\
\mbox{}\verb@@\\
\mbox{}\verb@  router<char> r;@\\
\mbox{}\verb@  vector<char> sorted[27];//one for each letter, one for default@\\
\mbox{}\verb@  word_sorter<back_insert_iterator<vector<char> > > *dummy[26];@\\
\mbox{}\verb@  for(int i = 0; i<26;i++)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    dummy[i] =@\\
\mbox{}\verb@     new word_sorter<back_insert_iterator<vector<char> > >@\\
\mbox{}\verb@     (back_inserter(sorted[i]),(char)(i + 97));@\\
\mbox{}\verb@    r.add_destination(*dummy[i]);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  my_default<back_insert_iterator<vector<char> > >@\\
\mbox{}\verb@   dflt(back_inserter(sorted[26]));@\\
\mbox{}\verb@  r.set_default(dflt);@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  vector<char> storage;@\\
\mbox{}\verb@  createinput(storage);  @\\
\mbox{}\verb@  @\\
\mbox{}\verb@  r.distribute(storage.begin(),storage.end());@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  for(int i = 0;i<26;i++)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    cout<<(char)(i + 97)<<": "<<sorted[i].size()<<endl;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  cout<<"Number of elements caught by default case: ";@\\
\mbox{}\verb@  cout<<sorted[26].size()<<endl;@\\
\mbox{}\verb@  if(validate(sorted))@\\
\mbox{}\verb@    cout<<"Passed Validation Test"<<endl;@\\
\mbox{}\verb@  else@\\
\mbox{}\verb@    cout<<"Failed Validation Test"<<endl;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  cout<<"\n*************     END OF RESULTS     *************\n\n"; @\\
\mbox{}\verb@@\\
\mbox{}\verb@  return 0;@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@\\
\mbox{}\verb@void createinput(vector<char> &storage)@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  for(int i = 0;i<27;i++)@\\
\mbox{}\verb@    for(int j = 0;j<1000;j++)@\\
\mbox{}\verb@      storage.push_back((char)(i+97));@\\
\mbox{}\verb@  random_shuffle(storage.begin(),storage.end());@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@\\
\mbox{}\verb@bool validate(vector<char> sorted[])@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  vector<char>::iterator iter;@\\
\mbox{}\verb@  for(int i = 0;i<27;i++)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    iter = sorted[i].begin();@\\
\mbox{}\verb@    for(;iter != sorted[i].end();iter++)@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      if(*iter != (char)(i + 97))@\\
\mbox{}\verb@      {@\\
\mbox{}\verb@        cout<<"Wrong letter: "<<*iter<<" should be ";@\\
\mbox{}\verb@        cout<<(char)(i + 97)<<" "<<i<<endl;@\\
\mbox{}\verb@        return false;@\\
\mbox{}\verb@        break;@\\
\mbox{}\verb@      }@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  return true;@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@
\end{list}
\vspace{-2ex}
\end{flushleft}
\subsection{Testing with \code{double}s}
\label{sec-code-test-double}
\begin{flushleft} \small \label{part113}
\verb@"test_double.cpp"@ {\footnotesize \hypertarget{211}{211} }$\equiv$
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@//test_double.cpp version 1.0@\\
\mbox{}\verb@#include <iostream>@\\
\mbox{}\verb@#include <fstream>@\\
\mbox{}\verb@#include <ctype.h>@\\
\mbox{}\verb@#include <algorithm>@\\
\mbox{}\verb@#include "router.hpp"@\\
\mbox{}\verb@using std::cout;@\\
\mbox{}\verb@using std::endl;@\\
\mbox{}\verb@using std::vector;@\\
\mbox{}\verb@using std::back_inserter;@\\
\mbox{}\verb@using std::istream_iterator;@\\
\mbox{}\verb@using std::back_insert_iterator;@\\
\mbox{}\verb@using std::cin;@\\
\mbox{}\verb@using std::min_element;@\\
\mbox{}\verb@using std::max_element;@\\
\mbox{}\verb@using gdfa::router;@\\
\mbox{}\verb@using gdfa::destination;@\\
\mbox{}\verb@@\\
\mbox{}\verb@void createinput(vector<double> &storage);@\\
\mbox{}\verb@bool validate(vector<double> sorted[]);@\\
\mbox{}\verb@@\\
\mbox{}\verb@class my_compare@\\
\mbox{}\verb@{@\\
\mbox{}\verb@public:@\\
\mbox{}\verb@  my_compare() {}@\\
\mbox{}\verb@  static const double epsilon = 1e-10;@\\
\mbox{}\verb@  bool less(const double &lhs,const double &rhs)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    if((rhs - lhs) < epsilon) return false;@\\
\mbox{}\verb@    if(lhs<rhs) return true;@\\
\mbox{}\verb@    return false;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  bool greater(const double &lhs,const double &rhs)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    if((lhs - rhs) < epsilon) return false;@\\
\mbox{}\verb@    if(lhs>rhs) return true;@\\
\mbox{}\verb@    return false;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  bool lessequal(const double &lhs,const double &rhs)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    if((rhs - lhs) < epsilon && (rhs - lhs) > -epsilon)@\\
\mbox{}\verb@     return true;@\\
\mbox{}\verb@    if(lhs<rhs) return true;@\\
\mbox{}\verb@    return false;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  bool greaterequal(const double &lhs,const double &rhs)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    if((lhs - rhs) < epsilon && (lhs - rhs) > -epsilon)@\\
\mbox{}\verb@     return true;@\\
\mbox{}\verb@    if(lhs>rhs) return true;@\\
\mbox{}\verb@    return false;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  bool equal(const double &lhs,const double &rhs)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    if((lhs - rhs) < epsilon && (rhs - lhs) < -epsilon)@\\
\mbox{}\verb@     return true;@\\
\mbox{}\verb@    if((rhs -lhs) < epsilon && (lhs - rhs) < -epsilon)@\\
\mbox{}\verb@     return true;@\\
\mbox{}\verb@    return false;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@@\\
\mbox{}\verb@};@\\
\mbox{}\verb@@\\
\mbox{}\verb@my_compare comp;@\\
\mbox{}\verb@@\\
\mbox{}\verb@template<typename output_iterator>@\\
\mbox{}\verb@class range_checker : public destination<double>@\\
\mbox{}\verb@{@\\
\mbox{}\verb@   private:@\\
\mbox{}\verb@      output_iterator m_out;@\\
\mbox{}\verb@      double m_lower;@\\
\mbox{}\verb@      double m_upper;@\\
\mbox{}\verb@//      static my_compare comp;@\\
\mbox{}\verb@      @\\
\mbox{}\verb@   public:@\\
\mbox{}\verb@      range_checker(output_iterator out, double lower,double upper)@\\
\mbox{}\verb@                 : m_out(out), m_lower(lower), m_upper(upper) {}@\\
\mbox{}\verb@      @\\
\mbox{}\verb@      /*out distribute function checks the first letter to see if@\\
\mbox{}\verb@      it is the same as in the predicate*/@\\
\mbox{}\verb@      bool distribute(const double& element)@\\
\mbox{}\verb@      {@\\
\mbox{}\verb@        if(comp.greater(element,m_lower) &&@\\
\mbox{}\verb@           comp.less(element,m_upper))@\\
\mbox{}\verb@        {@\\
\mbox{}\verb@            if( element < .3000000001 && element > .29999999)@\\
\mbox{}\verb@            {@\\
\mbox{}\verb@              cout<<"dumber than dirt "<<element<<endl;@\\
\mbox{}\verb@              cout<<element - m_lower<<endl;@\\
\mbox{}\verb@/*              if((element - m_lower) > epsilon)@\\
\mbox{}\verb@                cout<<"greater"<<endl;@\\
\mbox{}\verb@              if((m_lower - element) > epsilon)@\\
\mbox{}\verb@                cout<<"less than"<<endl;*/@\\
\mbox{}\verb@            }@\\
\mbox{}\verb@            *m_out++ = element;@\\
\mbox{}\verb@            return true;@\\
\mbox{}\verb@         }@\\
\mbox{}\verb@         @\\
\mbox{}\verb@         return false;@\\
\mbox{}\verb@      }@\\
\mbox{}\verb@};@\\
\mbox{}\verb@@\\
\mbox{}\verb@template<typename output_iterator>@\\
\mbox{}\verb@class my_default : public destination<double>@\\
\mbox{}\verb@{@\\
\mbox{}\verb@   private:@\\
\mbox{}\verb@      output_iterator m_out;@\\
\mbox{}\verb@   public:@\\
\mbox{}\verb@      my_default(output_iterator out)@\\
\mbox{}\verb@                 : m_out(out) {}@\\
\mbox{}\verb@      @\\
\mbox{}\verb@      bool distribute(const double& n)@\\
\mbox{}\verb@      {@\\
\mbox{}\verb@         *m_out++ = n;@\\
\mbox{}\verb@         return true;@\\
\mbox{}\verb@      }@\\
\mbox{}\verb@};@\\
\mbox{}\verb@@\\
\mbox{}\verb@int main(int argc,char *argv[])@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  cout << "\n\n\nTest:  test_double.cpp"@\\
\mbox{}\verb@    << "\n\nTest Using type double as input.\n"@\\
\mbox{}\verb@    << "***********************************\n\n"@\\
\mbox{}\verb@    << "Results:\n\n";@\\
\mbox{}\verb@@\\
\mbox{}\verb@  router<double> r;@\\
\mbox{}\verb@  vector<double> sorted[11];//one for each letter, one for default@\\
\mbox{}\verb@  range_checker<back_insert_iterator<vector<double> > > *dummy[10];@\\
\mbox{}\verb@  double lower = 0.0;@\\
\mbox{}\verb@  double upper = 0.1;@\\
\mbox{}\verb@  for(int i = 0; i<10;i++)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    dummy[i] =@\\
\mbox{}\verb@     new range_checker<back_insert_iterator<vector<double> > >@\\
\mbox{}\verb@     (back_inserter(sorted[i]), lower, upper);@\\
\mbox{}\verb@    r.add_destination(*dummy[i]);@\\
\mbox{}\verb@    lower+= 0.1;@\\
\mbox{}\verb@    upper+= 0.1;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  my_default<back_insert_iterator<vector<double> > >@\\
\mbox{}\verb@   dflt(back_inserter(sorted[10]));@\\
\mbox{}\verb@  r.set_default(dflt);@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  vector<double> storage;@\\
\mbox{}\verb@  createinput(storage);@\\
\mbox{}\verb@@\\
\mbox{}\verb@  r.distribute(storage.begin(),storage.end());@\\
\mbox{}\verb@  cout<<"number of elements in each range, with the max and min ";@\\
\mbox{}\verb@  cout<<"element in the ranges"<<endl;@\\
\mbox{}\verb@  double j;@\\
\mbox{}\verb@  int i;@\\
\mbox{}\verb@  for(i = 0,j = 0.0;i<10;i++,j+=.1)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    cout<<"("<<j<<","<<j+.1<<"): "<<sorted[i].size()<<" ";@\\
\mbox{}\verb@    cout<<*max_element(sorted[i].begin(),sorted[i].end())@\\
\mbox{}\verb@      <<" "<<*min_element(sorted[i].begin(),sorted[i].end())<<endl;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  cout<<"Number of elements caught by default case: ";@\\
\mbox{}\verb@  cout<<sorted[10].size()<<endl;@\\
\mbox{}\verb@  if(validate(sorted))@\\
\mbox{}\verb@    cout<<"Passed Validation Test"<<endl;@\\
\mbox{}\verb@  else@\\
\mbox{}\verb@    cout<<"Failed Validation Test"<<endl;@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  cout<<"\n*************     END OF RESULTS     *************\n\n";@\\
\mbox{}\verb@@\\
\mbox{}\verb@  return 0;@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@/*the key to this test is that we will generate the information @\\
\mbox{}\verb@to be filtered thus we can test if the filtering works correctly @\\
\mbox{}\verb@because we know what the solution is*/@\\
\mbox{}\verb@void createinput(vector<double> &storage)@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  double max = 1.0;@\\
\mbox{}\verb@  double increment = .000001;@\\
\mbox{}\verb@  double i;@\\
\mbox{}\verb@  for(i=0.0;comp.less(i,max);i+=increment)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    storage.push_back(i);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  random_shuffle(storage.begin(),storage.end());@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@\\
\mbox{}\verb@bool validate(vector<double> sorted[])@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  int i;@\\
\mbox{}\verb@  double j;@\\
\mbox{}\verb@  for(i = 0,j = 0.0;i<10;i++,j+=.1)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    double min = *min_element(sorted[i].begin(),sorted[i].end());@\\
\mbox{}\verb@    if(comp.greaterequal(j,min))@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      cout<<"Failed, "<<min<<" is not in range ";@\\
\mbox{}\verb@      cout<<"("<<j<<","<<j+.1<<")"<<endl;@\\
\mbox{}\verb@      return false;@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@    double max = *max_element(sorted[i].begin(),sorted[i].end());@\\
\mbox{}\verb@    if(comp.lessequal(j+.1,max))@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      cout<<"Failed, "<<max<<" is not in range ";@\\
\mbox{}\verb@      cout<<"("<<j<<","<<j+.1<<")"<<endl;@\\
\mbox{}\verb@      return false;@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  return true;@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@
\end{list}
\vspace{-2ex}
\end{flushleft}
\subsection{Testing with \code{int}s}
\label{sec-code-test-int}
\begin{flushleft} \small \label{part114}
\verb@"test_int.cpp"@ {\footnotesize \hypertarget{215}{215} }$\equiv$
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@//test_int.cpp version 1.0@\\
\mbox{}\verb@#include <iostream>@\\
\mbox{}\verb@#include <fstream>@\\
\mbox{}\verb@#include <ctype.h>@\\
\mbox{}\verb@#include "router.hpp"@\\
\mbox{}\verb@using std::cout;@\\
\mbox{}\verb@using std::endl;@\\
\mbox{}\verb@using std::vector;@\\
\mbox{}\verb@using std::back_inserter;@\\
\mbox{}\verb@using std::istream_iterator;@\\
\mbox{}\verb@using std::back_insert_iterator;@\\
\mbox{}\verb@using std::cin;@\\
\mbox{}\verb@@\\
\mbox{}\verb@using gdfa::router;@\\
\mbox{}\verb@using gdfa::destination;@\\
\mbox{}\verb@@\\
\mbox{}\verb@void createinput(vector<int> &storage);@\\
\mbox{}\verb@bool validate(vector<int> sorted[]);@\\
\mbox{}\verb@@\\
\mbox{}\verb@template<typename output_iterator>@\\
\mbox{}\verb@class range_checker : public destination<int>@\\
\mbox{}\verb@{@\\
\mbox{}\verb@   private:@\\
\mbox{}\verb@  output_iterator m_out;@\\
\mbox{}\verb@  int m_lower;@\\
\mbox{}\verb@      int m_upper; @\\
\mbox{}\verb@  @\\
\mbox{}\verb@   public:@\\
\mbox{}\verb@  range_checker(output_iterator out, int lower,int upper)@\\
\mbox{}\verb@         : m_out(out), m_lower(lower), m_upper(upper) {}@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  /*out distribute function checks the first letter to see if it is@\\
\mbox{}\verb@  the same as in the predicate*/@\\
\mbox{}\verb@  bool distribute(const int& element)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@     if(m_lower < element && m_upper > element)@\\
\mbox{}\verb@     {@\\
\mbox{}\verb@    *m_out++ = element;@\\
\mbox{}\verb@    return true;@\\
\mbox{}\verb@     }@\\
\mbox{}\verb@     @\\
\mbox{}\verb@     return false;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@};@\\
\mbox{}\verb@@\\
\mbox{}\verb@template<typename output_iterator>@\\
\mbox{}\verb@class my_default : public destination<int>@\\
\mbox{}\verb@{@\\
\mbox{}\verb@   private:@\\
\mbox{}\verb@  output_iterator m_out;@\\
\mbox{}\verb@   public:@\\
\mbox{}\verb@  my_default(output_iterator out)@\\
\mbox{}\verb@         : m_out(out) {}@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  bool distribute(const int& n)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@     *m_out++ = n;@\\
\mbox{}\verb@     return true;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@};@\\
\mbox{}\verb@@\\
\mbox{}\verb@int main(int argc,char *argv[])@\\
\mbox{}\verb@{@\\
\mbox{}\verb@    cout << "\n\n\nTest:  test_int.cpp"@\\
\mbox{}\verb@    << "\n\nTest Using integers as input.\n"@\\
\mbox{}\verb@    << "***********************************\n\n"@\\
\mbox{}\verb@    << "Results:\n\n";@\\
\mbox{}\verb@@\\
\mbox{}\verb@  router<int> r;@\\
\mbox{}\verb@  vector<int> sorted[11];//one for each letter, one for default@\\
\mbox{}\verb@  range_checker<back_insert_iterator<vector<int> > > *dummy[10];@\\
\mbox{}\verb@  int lower = 0;@\\
\mbox{}\verb@  int upper = 100000;@\\
\mbox{}\verb@  for(int i = 0; i<10;i++)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    dummy[i] =@\\
\mbox{}\verb@     new range_checker<back_insert_iterator<vector<int> > >@\\
\mbox{}\verb@     (back_inserter(sorted[i]), lower, upper);@\\
\mbox{}\verb@    r.add_destination(*dummy[i]);@\\
\mbox{}\verb@    lower+= 100000;@\\
\mbox{}\verb@    upper+= 100000;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  my_default<back_insert_iterator<vector<int> > >@\\
\mbox{}\verb@   dflt(back_inserter(sorted[10]));@\\
\mbox{}\verb@  r.set_default(dflt);@\\
\mbox{}\verb@  vector<int> storage;@\\
\mbox{}\verb@  createinput(storage);@\\
\mbox{}\verb@@\\
\mbox{}\verb@  r.distribute(storage.begin(),storage.end());@\\
\mbox{}\verb@  cout<<"number of elements in each range, with the max and min ";@\\
\mbox{}\verb@  cout<<"element in the ranges"<<endl;@\\
\mbox{}\verb@  for(int i = 0;i<10;i++)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    cout<<"("<<i * 100000<<","<<(i+1)*100000<<"): ";@\\
\mbox{}\verb@    cout<<sorted[i].size()<<" ";@\\
\mbox{}\verb@    cout<<*max_element(sorted[i].begin(),sorted[i].end())@\\
\mbox{}\verb@      <<" "<<*min_element(sorted[i].begin(),sorted[i].end())<<endl;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  cout<<"Number elements caught by default case: ";@\\
\mbox{}\verb@  cout<<sorted[10].size()<<endl;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  if(validate(sorted))@\\
\mbox{}\verb@    cout<<"Passed Validation Test"<<endl;@\\
\mbox{}\verb@  else@\\
\mbox{}\verb@    cout<<"Failed Validation Test"<<endl;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  cout<<"\n*************     END OF RESULTS     *************\n\n";@\\
\mbox{}\verb@@\\
\mbox{}\verb@  return 0;@\\
\mbox{}\verb@}@\\
\mbox{}\verb@/*the key to this test is that we will generate the information @\\
\mbox{}\verb@to be filtered thus we can test if the filtering works correctly @\\
\mbox{}\verb@because we know what the solution is*/@\\
\mbox{}\verb@void createinput(vector<int> &storage)@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  int max = 1000000;@\\
\mbox{}\verb@  for(int i=0;i<max;i++)@\\
\mbox{}\verb@    storage.push_back(i);@\\
\mbox{}\verb@  random_shuffle(storage.begin(),storage.end());@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@\\
\mbox{}\verb@bool validate(vector<int> sorted[])@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  int i;@\\
\mbox{}\verb@  int j = 0;@\\
\mbox{}\verb@  for(i = 0,j=0;i<10;i++,j+=100000)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    int min = *min_element(sorted[i].begin(),sorted[i].end());@\\
\mbox{}\verb@    if(j>=min)@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      cout<<"Failed, "<<min<<" is not in range ";@\\
\mbox{}\verb@      cout<<"("<<j<<","<<j+100000<<")"<<endl;@\\
\mbox{}\verb@      return false;@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@    double max = *max_element(sorted[i].begin(),sorted[i].end());@\\
\mbox{}\verb@    if(j+100000 <= max)@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      cout<<"Failed, "<<max<<" is not in range ";@\\
\mbox{}\verb@      cout<<"("<<j<<","<<j+100000<<")"<<endl;@\\
\mbox{}\verb@      return false;@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  return true;@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@
\end{list}
\vspace{-2ex}
\end{flushleft}
\subsection{Testing with \code{std::string}s}
\label{sec-code-test-string}
\begin{flushleft} \small \label{part115}
\verb@"test_string.cpp"@ {\footnotesize \hypertarget{218}{218} }$\equiv$
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@//test_string.cpp version 1.0@\\
\mbox{}\verb@#include <iostream>@\\
\mbox{}\verb@#include <fstream>@\\
\mbox{}\verb@#include <string>@\\
\mbox{}\verb@#include <ctype.h>@\\
\mbox{}\verb@#include "router.hpp"@\\
\mbox{}\verb@using std::cout;@\\
\mbox{}\verb@using std::endl;@\\
\mbox{}\verb@using std::vector;@\\
\mbox{}\verb@using std::back_inserter;@\\
\mbox{}\verb@using std::istream_iterator;@\\
\mbox{}\verb@using std::back_insert_iterator;@\\
\mbox{}\verb@using std::string;@\\
\mbox{}\verb@using std::cin;@\\
\mbox{}\verb@@\\
\mbox{}\verb@using gdfa::router;@\\
\mbox{}\verb@using gdfa::destination;@\\
\mbox{}\verb@@\\
\mbox{}\verb@void createinput(vector<string> &storage);@\\
\mbox{}\verb@bool validate(vector<string> sorted[]);@\\
\mbox{}\verb@@\\
\mbox{}\verb@template<typename output_iterator>@\\
\mbox{}\verb@class word_sorter : public destination<string>@\\
\mbox{}\verb@{@\\
\mbox{}\verb@   private:@\\
\mbox{}\verb@  output_iterator m_out;@\\
\mbox{}\verb@  char m_first_letter;@\\
\mbox{}\verb@  @\\
\mbox{}\verb@   public:@\\
\mbox{}\verb@  word_sorter(output_iterator out, char first_letter)@\\
\mbox{}\verb@         : m_out(out), m_first_letter(first_letter) {}@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  /*out distribute function checks the first letter to see if it is@\\
\mbox{}\verb@  the same as in the predicate*/@\\
\mbox{}\verb@  bool distribute(const string& element)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@     if (tolower((const int)element[0]) == m_first_letter)@\\
\mbox{}\verb@     {@\\
\mbox{}\verb@    *m_out++ = element;@\\
\mbox{}\verb@    return true;@\\
\mbox{}\verb@     }@\\
\mbox{}\verb@     @\\
\mbox{}\verb@     return false;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@};@\\
\mbox{}\verb@@\\
\mbox{}\verb@template<typename output_iterator>@\\
\mbox{}\verb@class my_default : public destination<string>@\\
\mbox{}\verb@{@\\
\mbox{}\verb@   private:@\\
\mbox{}\verb@  output_iterator m_out;@\\
\mbox{}\verb@   public:@\\
\mbox{}\verb@  my_default(output_iterator out)@\\
\mbox{}\verb@         : m_out(out) {}@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  bool distribute(const string& n)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@     *m_out++ = n;@\\
\mbox{}\verb@     return true;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@};@\\
\mbox{}\verb@@\\
\mbox{}\verb@int main(int argc,char *argv[])@\\
\mbox{}\verb@{@\\
\mbox{}\verb@    cout << "\n\n\nTest:  test_string.cpp"@\\
\mbox{}\verb@    << "\n\nTest Using strings as input.\n"@\\
\mbox{}\verb@    << "***********************************\n\n"@\\
\mbox{}\verb@    << "Results:\n\n";@\\
\mbox{}\verb@@\\
\mbox{}\verb@  router<string> r;@\\
\mbox{}\verb@  vector<string> sorted[27];//one for each letter, one for default@\\
\mbox{}\verb@  word_sorter<back_insert_iterator<vector<string> > > *dummy[26];@\\
\mbox{}\verb@  for(int i = 0; i<26;i++)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    dummy[i] =@\\
\mbox{}\verb@     new word_sorter<back_insert_iterator<vector<string> > >@\\
\mbox{}\verb@     (back_inserter(sorted[i]),(char)(i + 97));@\\
\mbox{}\verb@    r.add_destination(*dummy[i]);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  my_default<back_insert_iterator<vector<string> > >@\\
\mbox{}\verb@   dflt(back_inserter(sorted[26]));@\\
\mbox{}\verb@  r.set_default(dflt);@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  vector<string> storage;@\\
\mbox{}\verb@  createinput(storage);@\\
\mbox{}\verb@  r.distribute(storage.begin(),storage.end());@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  for(int i = 0;i<26;i++)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    cout<<(char)(i + 97)<<": "<<sorted[i].size()<<endl;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  cout<<"Number of elements caught by default case: ";@\\
\mbox{}\verb@  cout<<sorted[26].size()<<endl;@\\
\mbox{}\verb@  if(validate(sorted))@\\
\mbox{}\verb@    cout<<"Passed Validation Test"<<endl;@\\
\mbox{}\verb@  else@\\
\mbox{}\verb@    cout<<"Failed Validation Test"<<endl;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  cout<<"\n*************     END OF RESULTS     *************\n\n";@\\
\mbox{}\verb@@\\
\mbox{}\verb@  return 0;@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@\\
\mbox{}\verb@void createinput(vector<string> &storage)@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  for(int i = 0;i<27;i++)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    for(int j = 0;j < 27;j++)@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      for(int k = 0;k<27;k++)@\\
\mbox{}\verb@      {@\\
\mbox{}\verb@        string foo;@\\
\mbox{}\verb@        foo += (char)(i + 97);@\\
\mbox{}\verb@        foo += (char)(j + 97);@\\
\mbox{}\verb@        foo += (char)(k + 97);@\\
\mbox{}\verb@        storage.push_back(foo);@\\
\mbox{}\verb@      }@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  random_shuffle(storage.begin(),storage.end());@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@\\
\mbox{}\verb@bool validate(vector<string> sorted[])@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  vector<string>::iterator iter;@\\
\mbox{}\verb@  for(int i = 0;i<27;i++)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    iter = sorted[i].begin();@\\
\mbox{}\verb@    for(;iter != sorted[i].end();iter++)@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      if((*iter)[0] != (char)(i + 97))@\\
\mbox{}\verb@      {@\\
\mbox{}\verb@        cout<<"Wrong letter: "<<*iter<<" should be ";@\\
\mbox{}\verb@        cout<<(char)(i + 97)<<" "<<i<<endl;@\\
\mbox{}\verb@        return false;@\\
\mbox{}\verb@        break;@\\
\mbox{}\verb@      }@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  return true;@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@
\end{list}
\vspace{-2ex}
\end{flushleft}
\section{Priority Testing}
\label{sec-priority-tests}
\subsection{2-Priority Tests}
\subsubsection{2-Priority with Fall-Through}
\label{sec-code-test-2pt-f}
\begin{flushleft} \small \label{part116}
\verb@"priority2_fallthrough.cpp"@ {\footnotesize \hypertarget{221}{221} }$\equiv$
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@//priority2_fallthrough.cpp version 1.1@\\
\mbox{}\verb@#include <vector>@\\
\mbox{}\verb@#include <iostream>@\\
\mbox{}\verb@#include <fstream>@\\
\mbox{}\verb@#include <string>@\\
\mbox{}\verb@#include <ctype.h>@\\
\mbox{}\verb@#include "router.hpp"@\\
\mbox{}\verb@#include "test_classes_fallthrough.hpp"@\\
\mbox{}\verb@using std::cout;@\\
\mbox{}\verb@using std::endl;@\\
\mbox{}\verb@using std::vector;@\\
\mbox{}\verb@using std::back_inserter;@\\
\mbox{}\verb@using std::istream_iterator;@\\
\mbox{}\verb@using std::back_insert_iterator;@\\
\mbox{}\verb@using std::string;@\\
\mbox{}\verb@using std::cin;@\\
\mbox{}\verb@@\\
\mbox{}\verb@using gdfa::router;@\\
\mbox{}\verb@using gdfa::destination;@\\
\mbox{}\verb@@\\
\mbox{}\verb@bool validate(vector<string> sorted[]);@\\
\mbox{}\verb@@\\
\mbox{}\verb@template<typename InputIterator>@\\
\mbox{}\verb@bool testpriority(router<string>::priority_level p1,@\\
\mbox{}\verb@ router<string>::priority_level p2,@\\
\mbox{}\verb@    InputIterator begin,InputIterator end)@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  router<string> r;//router@\\
\mbox{}\verb@  vector<string> sorted[29];//one for each letter, one for default@\\
\mbox{}\verb@   //2 for length filtering@\\
\mbox{}\verb@  word_sorter<back_insert_iterator<vector<string> > >@\\
\mbox{}\verb@   *dummy[26];//general sorters@\\
\mbox{}\verb@@\\
\mbox{}\verb@  length_counter<back_insert_iterator<vector<string> > >@\\
\mbox{}\verb@   length1(back_inserter(sorted[0]),1);//sorts by length@\\
\mbox{}\verb@  length_counter<back_insert_iterator<vector<string> > >@\\
\mbox{}\verb@   length2(back_inserter(sorted[1]),2);@\\
\mbox{}\verb@@\\
\mbox{}\verb@  r.add_destination(length1,p1);@\\
\mbox{}\verb@  r.add_destination(length2,p1);@\\
\mbox{}\verb@  for(int i = 0; i<26;i++)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    dummy[i] =@\\
\mbox{}\verb@     new word_sorter<back_insert_iterator<vector<string> > >@\\
\mbox{}\verb@     (back_inserter(sorted[i+2]),(char)(i + 97));@\\
\mbox{}\verb@    r.add_destination(*dummy[i],p2);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  my_default<back_insert_iterator<vector<string> > >@\\
\mbox{}\verb@   dflt(back_inserter(sorted[28]));@\\
\mbox{}\verb@  r.set_default(dflt);@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  r.distribute(begin,end);@\\
\mbox{}\verb@  return validate(sorted);@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@\\
\mbox{}\verb@/*with this test we are testing the back inserter for output and@\\
\mbox{}\verb@istream_iterator<string> for input*/@\\
\mbox{}\verb@@\\
\mbox{}\verb@/*for testing from standard in we will sort words by their first@\\
\mbox{}\verb@letter we would like to be able to count the number of words that@\\
\mbox{}\verb@begin with each letter*/@\\
\mbox{}\verb@@\\
\mbox{}\verb@int main(int argc,char *argv[])@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  cout << "\n\n\nTest:  priority2_fallthrough.cpp\n\n"@\\
\mbox{}\verb@  <<"Test router with 2 priorities (allowing fall through)\n"@\\
\mbox{}\verb@  <<"******************************"@\\
\mbox{}\verb@  <<"*****************************\n\n"@\\
\mbox{}\verb@  <<"Note: Fall through means that a destination\n"@\\
\mbox{}\verb@  <<"passes the element on to the next destination.\n\n"@\\
\mbox{}\verb@  <<"**********************************************\n\n"@\\
\mbox{}\verb@  <<"Results:\n\n";@\\
\mbox{}\verb@@\\
\mbox{}\verb@  router<string> r;//router@\\
\mbox{}\verb@  vector<string> sorted[29];//one for each letter, one for default@\\
\mbox{}\verb@   //2 for length filtering@\\
\mbox{}\verb@  word_sorter<back_insert_iterator<vector<string> > >@\\
\mbox{}\verb@   *dummy[26];//general sorters@\\
\mbox{}\verb@@\\
\mbox{}\verb@  length_counter<back_insert_iterator<vector<string> > >@\\
\mbox{}\verb@   length1(back_inserter(sorted[0]),1);//sorts by length@\\
\mbox{}\verb@  length_counter<back_insert_iterator<vector<string> > >@\\
\mbox{}\verb@   length2(back_inserter(sorted[1]),2);@\\
\mbox{}\verb@@\\
\mbox{}\verb@  r.add_destination(length1,router<string>::urgent_priority);@\\
\mbox{}\verb@  r.add_destination(length2,router<string>::urgent_priority);@\\
\mbox{}\verb@  for(int i = 0; i<26;i++)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    dummy[i] =@\\
\mbox{}\verb@     new word_sorter<back_insert_iterator<vector<string> > >@\\
\mbox{}\verb@     (back_inserter(sorted[i+2]),(char)(i + 97));@\\
\mbox{}\verb@    r.add_destination(*dummy[i],router<string>::high_priority);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  my_default<back_insert_iterator<vector<string> > >@\\
\mbox{}\verb@   dflt(back_inserter(sorted[28]));@\\
\mbox{}\verb@  r.set_default(dflt);@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  //we want to create our own input for validation purposes@\\
\mbox{}\verb@  vector<string> storage_for_later;@\\
\mbox{}\verb@  createinputstring(storage_for_later);@\\
\mbox{}\verb@@\\
\mbox{}\verb@  //distribute@\\
\mbox{}\verb@  r.distribute(storage_for_later.begin(),storage_for_later.end());@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  cout<<"results of testing urgent priority and high priority";@\\
\mbox{}\verb@  cout<<endl;@\\
\mbox{}\verb@  cout<<"words of length 1: "<<sorted[0].size()<<endl;@\\
\mbox{}\verb@  cout<<"words of length 2: "<<sorted[1].size()<<endl;@\\
\mbox{}\verb@  cout<<"counts for all other words, based on starting ";@\\
\mbox{}\verb@  cout<<"character (case insensitive)"<<endl;@\\
\mbox{}\verb@  for(int i = 0;i<26;i++)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    cout<<(char)(i + 97)<<": "<<sorted[i + 2].size()<<endl;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  cout<<"Default: "<<sorted[28].size()<<endl;@\\
\mbox{}\verb@  if(validate(sorted))@\\
\mbox{}\verb@    cout<<"Passed test for urgent and high priorities"<<endl;@\\
\mbox{}\verb@  else@\\
\mbox{}\verb@    cout<<"Failed test for urgent and high priorities"<<endl;@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  @\\
\mbox{}\verb@  @\\
\mbox{}\verb@  cout<<"Testing Urgent and normal priority"<<endl;@\\
\mbox{}\verb@  if(testpriority(router<string>::urgent_priority,@\\
\mbox{}\verb@     router<string>::normal_priority,@\\
\mbox{}\verb@     storage_for_later.begin(),storage_for_later.end()))@\\
\mbox{}\verb@    cout<<"Passed test for urgent and normal priority"<<endl;@\\
\mbox{}\verb@  else@\\
\mbox{}\verb@    cout<<"Failed test for urgent and normal priority"<<endl;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  cout<<"Testing Urgent and low priority"<<endl;@\\
\mbox{}\verb@  if(testpriority(router<string>::urgent_priority,@\\
\mbox{}\verb@     router<string>::low_priority,@\\
\mbox{}\verb@     storage_for_later.begin(),storage_for_later.end()))@\\
\mbox{}\verb@    cout<<"Passed test for urgent and low priority"<<endl;@\\
\mbox{}\verb@  else@\\
\mbox{}\verb@    cout<<"Failed test for urgent and low priority"<<endl;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  cout<<"Testing high and normal priority"<<endl;@\\
\mbox{}\verb@  if(testpriority(router<string>::high_priority,@\\
\mbox{}\verb@     router<string>::normal_priority,@\\
\mbox{}\verb@     storage_for_later.begin(),storage_for_later.end()))@\\
\mbox{}\verb@    cout<<"Passed test for high and normal priority"<<endl;@\\
\mbox{}\verb@  else@\\
\mbox{}\verb@    cout<<"Failed test for high and normal priority"<<endl;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  cout<<"Testing high and low priority"<<endl;@\\
\mbox{}\verb@  if(testpriority(router<string>::high_priority,@\\
\mbox{}\verb@     router<string>::low_priority,@\\
\mbox{}\verb@     storage_for_later.begin(),storage_for_later.end()))@\\
\mbox{}\verb@    cout<<"Passed test for high and low priority"<<endl;@\\
\mbox{}\verb@  else@\\
\mbox{}\verb@    cout<<"Failed test for high and low priority"<<endl;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  cout<<"Testing normal and low priority"<<endl;@\\
\mbox{}\verb@  if(testpriority(router<string>::normal_priority,@\\
\mbox{}\verb@     router<string>::low_priority,@\\
\mbox{}\verb@     storage_for_later.begin(),storage_for_later.end()))@\\
\mbox{}\verb@    cout<<"Passed test for normal and low priority"<<endl;@\\
\mbox{}\verb@  else@\\
\mbox{}\verb@    cout<<"Failed test for normal and low priority"<<endl;@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@  cout<<"\n*************     END OF RESULTS     *************\n\n";@\\
\mbox{}\verb@@\\
\mbox{}\verb@  return 0;@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@\\
\mbox{}\verb@bool validate(vector<string> sorted[])@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  vector<string>::iterator iter;@\\
\mbox{}\verb@  if(sorted[0].size() != 19683)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    cout<<"Length 1 failed"<<endl;@\\
\mbox{}\verb@    return false;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  else@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    //check every string to make sure it is of length 1@\\
\mbox{}\verb@    for(iter = sorted[0].begin();iter != sorted[0].end();iter++)@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      if((*iter).size() != 1)@\\
\mbox{}\verb@      {@\\
\mbox{}\verb@        cout<<"String in length 1 container contains a string of ";@\\
\mbox{}\verb@        cout<<"not length 1"<<endl;@\\
\mbox{}\verb@        return false;@\\
\mbox{}\verb@      }@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  if(sorted[1].size() != 19683)  @\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    cout<<"Length 2 failed"<<endl;@\\
\mbox{}\verb@    return false;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  else@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    //check every string to make sure it is of length 2@\\
\mbox{}\verb@    for(iter = sorted[1].begin();iter != sorted[1].end();iter++)@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      if((*iter).size() != 2)@\\
\mbox{}\verb@      {@\\
\mbox{}\verb@        cout<<"String in length 2 container contains a string of ";@\\
\mbox{}\verb@        cout<<"not length 2"<<endl;@\\
\mbox{}\verb@        return false;@\\
\mbox{}\verb@      }@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  for(int i = 2;i<28;i++)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    if(sorted[i].size() != 2187)@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      cout<<"Begins letter """<<(char)(i+95)<<""" failed"<<endl;@\\
\mbox{}\verb@      return false;@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@    else@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      /*check each string to make sure it starts with the correct@\\
\mbox{}\verb@      letter*/@\\
\mbox{}\verb@      for(iter = sorted[i].begin();iter != sorted[i].end();iter++)@\\
\mbox{}\verb@      {@\\
\mbox{}\verb@        if((*iter)[0] != (char)(i+95))@\\
\mbox{}\verb@        {@\\
\mbox{}\verb@          cout<<"String in begins with "<<(char)(i+95);@\\
\mbox{}\verb@          cout<<" container ";@\\
\mbox{}\verb@          cout<<"contains a string beginning with ";@\\
\mbox{}\verb@          cout<<(*iter)[0]<<endl;@\\
\mbox{}\verb@          return false;@\\
\mbox{}\verb@        }@\\
\mbox{}\verb@      }@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  if(sorted[28].size() != 59049)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    cout<<"Default case failed"<<endl;@\\
\mbox{}\verb@    return false;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  return true;@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@
\end{list}
\vspace{-2ex}
\end{flushleft}
\subsubsection{2-Priority without Fall-Through}
\label{sec-code-test-2pt-n}
\begin{flushleft} \small \label{part117}
\verb@"priority2_nofallthrough.cpp"@ {\footnotesize \hypertarget{226}{226} }$\equiv$
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@//priority2_nofallthrough.cpp version 1.1@\\
\mbox{}\verb@#include <vector>@\\
\mbox{}\verb@#include <iostream>@\\
\mbox{}\verb@#include <fstream>@\\
\mbox{}\verb@#include <string>@\\
\mbox{}\verb@#include <ctype.h>@\\
\mbox{}\verb@#include "router.hpp"@\\
\mbox{}\verb@#include "test_classes.hpp"@\\
\mbox{}\verb@using std::cout;@\\
\mbox{}\verb@using std::endl;@\\
\mbox{}\verb@using std::vector;@\\
\mbox{}\verb@using std::back_inserter;@\\
\mbox{}\verb@using std::istream_iterator;@\\
\mbox{}\verb@using std::back_insert_iterator;@\\
\mbox{}\verb@using std::string;@\\
\mbox{}\verb@using std::cin;@\\
\mbox{}\verb@@\\
\mbox{}\verb@using gdfa::router;@\\
\mbox{}\verb@using gdfa::destination;@\\
\mbox{}\verb@@\\
\mbox{}\verb@bool validate(vector<string> sorted[]);@\\
\mbox{}\verb@@\\
\mbox{}\verb@template<typename InputIterator>@\\
\mbox{}\verb@bool testpriority(router<string>::priority_level p1,@\\
\mbox{}\verb@ router<string>::priority_level p2,@\\
\mbox{}\verb@ InputIterator begin,InputIterator end)@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  router<string> r;//router@\\
\mbox{}\verb@  vector<string> sorted[29];//one for each letter, one for default,@\\
\mbox{}\verb@   //2 for length filtering@\\
\mbox{}\verb@  word_sorter<back_insert_iterator<vector<string> > >@\\
\mbox{}\verb@   *dummy[26];//general sorters@\\
\mbox{}\verb@@\\
\mbox{}\verb@  length_counter<back_insert_iterator<vector<string> > >@\\
\mbox{}\verb@   length1(back_inserter(sorted[0]),1);//sorts by length@\\
\mbox{}\verb@  length_counter<back_insert_iterator<vector<string> > >@\\
\mbox{}\verb@   length2(back_inserter(sorted[1]),2);@\\
\mbox{}\verb@@\\
\mbox{}\verb@  r.add_destination(length1,p1);@\\
\mbox{}\verb@  r.add_destination(length2,p1);@\\
\mbox{}\verb@  for(int i = 0; i<26;i++)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    dummy[i] =@\\
\mbox{}\verb@     new word_sorter<back_insert_iterator<vector<string> > >@\\
\mbox{}\verb@     (back_inserter(sorted[i+2]),(char)(i + 97));@\\
\mbox{}\verb@    r.add_destination(*dummy[i],p2);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  my_default<back_insert_iterator<vector<string> > >@\\
\mbox{}\verb@   dflt(back_inserter(sorted[28]));@\\
\mbox{}\verb@  r.set_default(dflt);@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  r.distribute(begin,end);@\\
\mbox{}\verb@  return validate(sorted);@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@\\
\mbox{}\verb@/*with this test we are testing the back inserter for output and@\\
\mbox{}\verb@istream_iterator<string> for input*/@\\
\mbox{}\verb@@\\
\mbox{}\verb@/*for testing from standard in we will sort words by their first@\\
\mbox{}\verb@letter we would like to be able to count the number of words that@\\
\mbox{}\verb@begin with each letter*/@\\
\mbox{}\verb@@\\
\mbox{}\verb@int main(int argc,char *argv[])@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  cout << "\n\n\nTest:  priority2_nofallthrough.cpp\n\n"@\\
\mbox{}\verb@    << "Test router with 2 priorities (No fall through)\n"@\\
\mbox{}\verb@    << "***********************************************\n\n"@\\
\mbox{}\verb@    << "(Note: Fall through means that a destination\n"@\\
\mbox{}\verb@    << "passes the element on to the next destination.\n\n"@\\
\mbox{}\verb@    << "**********************************************\n\n"@\\
\mbox{}\verb@    << "Results:\n\n";@\\
\mbox{}\verb@@\\
\mbox{}\verb@  router<string> r;//router@\\
\mbox{}\verb@  vector<string> sorted[29];//one for each letter, one for default,@\\
\mbox{}\verb@   //2 for length filtering@\\
\mbox{}\verb@  word_sorter<back_insert_iterator<vector<string> > >@\\
\mbox{}\verb@   *dummy[26];//general sorters@\\
\mbox{}\verb@@\\
\mbox{}\verb@  length_counter<back_insert_iterator<vector<string> > >@\\
\mbox{}\verb@   length1(back_inserter(sorted[0]),1);//sorts by length@\\
\mbox{}\verb@  length_counter<back_insert_iterator<vector<string> > >@\\
\mbox{}\verb@   length2(back_inserter(sorted[1]),2);@\\
\mbox{}\verb@@\\
\mbox{}\verb@  r.add_destination(length1,router<string>::urgent_priority);@\\
\mbox{}\verb@  r.add_destination(length2,router<string>::urgent_priority);@\\
\mbox{}\verb@  for(int i = 0; i<26;i++)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    dummy[i] =@\\
\mbox{}\verb@     new word_sorter<back_insert_iterator<vector<string> > >@\\
\mbox{}\verb@     (back_inserter(sorted[i+2]),(char)(i + 97));@\\
\mbox{}\verb@    r.add_destination(*dummy[i],router<string>::high_priority);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  my_default<back_insert_iterator<vector<string> > >@\\
\mbox{}\verb@   dflt(back_inserter(sorted[28]));@\\
\mbox{}\verb@  r.set_default(dflt);@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  //we want to create our own input for validation purposes@\\
\mbox{}\verb@  vector<string> storage_for_later;@\\
\mbox{}\verb@  createinputstring(storage_for_later);@\\
\mbox{}\verb@@\\
\mbox{}\verb@  //distribute@\\
\mbox{}\verb@  r.distribute(storage_for_later.begin(),storage_for_later.end());@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  cout<<"results of testing urgent priority and high priority";@\\
\mbox{}\verb@  cout<<endl;@\\
\mbox{}\verb@  cout<<"words of length 1: "<<sorted[0].size()<<endl;@\\
\mbox{}\verb@  cout<<"words of length 2: "<<sorted[1].size()<<endl;@\\
\mbox{}\verb@  cout<<"counts for all other words, based on starting character ";@\\
\mbox{}\verb@  cout<<"(case insensitive)"<<endl;@\\
\mbox{}\verb@  for(int i = 0;i<26;i++)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    cout<<(char)(i + 97)<<": "<<sorted[i + 2].size()<<endl;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  cout<<"Default: "<<sorted[28].size()<<endl;@\\
\mbox{}\verb@  if(validate(sorted))@\\
\mbox{}\verb@    cout<<"Passed test for urgent and high priorities"<<endl;@\\
\mbox{}\verb@  else@\\
\mbox{}\verb@    cout<<"Failed test for urgent and high priorities"<<endl;@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@  cout<<"Testing Urgent and normal priority"<<endl;@\\
\mbox{}\verb@  if(testpriority(router<string>::urgent_priority,@\\
\mbox{}\verb@     router<string>::normal_priority,@\\
\mbox{}\verb@     storage_for_later.begin(),storage_for_later.end()))@\\
\mbox{}\verb@    cout<<"Passed test for urgent and normal priority"<<endl;@\\
\mbox{}\verb@  else@\\
\mbox{}\verb@    cout<<"Failed test for urgent and normal priority"<<endl;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  cout<<"Testing Urgent and low priority"<<endl;@\\
\mbox{}\verb@  if(testpriority(router<string>::urgent_priority,@\\
\mbox{}\verb@     router<string>::low_priority,@\\
\mbox{}\verb@     storage_for_later.begin(),storage_for_later.end()))@\\
\mbox{}\verb@    cout<<"Passed test for urgent and low priority"<<endl;@\\
\mbox{}\verb@  else@\\
\mbox{}\verb@    cout<<"Failed test for urgent and low priority"<<endl;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  cout<<"Testing high and normal priority"<<endl;@\\
\mbox{}\verb@  if(testpriority(router<string>::high_priority,@\\
\mbox{}\verb@     router<string>::normal_priority,@\\
\mbox{}\verb@     storage_for_later.begin(),storage_for_later.end()))@\\
\mbox{}\verb@    cout<<"Passed test for high and normal priority"<<endl;@\\
\mbox{}\verb@  else@\\
\mbox{}\verb@    cout<<"Failed test for high and normal priority"<<endl;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  cout<<"Testing high and low priority"<<endl;@\\
\mbox{}\verb@  if(testpriority(router<string>::high_priority,@\\
\mbox{}\verb@     router<string>::low_priority,@\\
\mbox{}\verb@     storage_for_later.begin(),storage_for_later.end()))@\\
\mbox{}\verb@    cout<<"Passed test for high and low priority"<<endl;@\\
\mbox{}\verb@  else@\\
\mbox{}\verb@    cout<<"Failed test for high and low priority"<<endl;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  cout<<"Testing normal and low priority"<<endl;@\\
\mbox{}\verb@  if(testpriority(router<string>::normal_priority,@\\
\mbox{}\verb@     router<string>::low_priority,@\\
\mbox{}\verb@     storage_for_later.begin(),storage_for_later.end()))@\\
\mbox{}\verb@    cout<<"Passed test for normal and low priority"<<endl;@\\
\mbox{}\verb@  else@\\
\mbox{}\verb@    cout<<"Failed test for normal and low priority"<<endl;@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@  cout<<"\n*************     END OF RESULTS     *************\n\n";@\\
\mbox{}\verb@@\\
\mbox{}\verb@  return 0;@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@\\
\mbox{}\verb@bool validate(vector<string> sorted[])@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  vector<string>::iterator iter;@\\
\mbox{}\verb@  if(sorted[0].size() != 19683)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    cout<<"Length 1 failed"<<endl;@\\
\mbox{}\verb@    return false;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  else@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    //check every string to make sure it is of length 1@\\
\mbox{}\verb@    for(iter = sorted[0].begin();iter != sorted[0].end();iter++)@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      if((*iter).size() != 1)@\\
\mbox{}\verb@      {@\\
\mbox{}\verb@        cout<<"String in length 1 container contains a string of ";@\\
\mbox{}\verb@        cout<<"not length 1"<<endl;@\\
\mbox{}\verb@        return false;@\\
\mbox{}\verb@      }@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  if(sorted[1].size() != 19683)  @\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    cout<<"Length 2 failed"<<endl;@\\
\mbox{}\verb@    return false;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  else@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    //check every string to make sure it is of length 2@\\
\mbox{}\verb@    for(iter = sorted[1].begin();iter != sorted[1].end();iter++)@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      if((*iter).size() != 2)@\\
\mbox{}\verb@      {@\\
\mbox{}\verb@        cout<<"String in length 2 container contains a string of ";@\\
\mbox{}\verb@        cout<<"not length 2"<<endl;@\\
\mbox{}\verb@        return false;@\\
\mbox{}\verb@      }@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  for(int i = 2;i<28;i++)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    if(sorted[i].size() != 729)@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      cout<<"Begins letter """<<(char)(i+95)<<""" failed"<<endl;@\\
\mbox{}\verb@      return false;@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@    else@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      /*check each string to make sure it starts with the correct@\\
\mbox{}\verb@      letter*/@\\
\mbox{}\verb@      for(iter = sorted[i].begin();iter != sorted[i].end();iter++)@\\
\mbox{}\verb@      {@\\
\mbox{}\verb@        if((*iter)[0] != (char)(i+95))@\\
\mbox{}\verb@        {@\\
\mbox{}\verb@          cout<<"String in begins with "<<(char)(i+95);@\\
\mbox{}\verb@          cout<<" container ";@\\
\mbox{}\verb@          cout<<"contains a string beginning with ";@\\
\mbox{}\verb@          cout<<(*iter)[0]<<endl;@\\
\mbox{}\verb@          return false;@\\
\mbox{}\verb@        }@\\
\mbox{}\verb@        /*also need to check that the string length of the@\\
\mbox{}\verb@        string is greater than 2*/@\\
\mbox{}\verb@        if((*iter).size() < 3)@\\
\mbox{}\verb@        {@\\
\mbox{}\verb@          cout<<"Begins letter """<<(char)(i+94)<<""" contains a ";@\\
\mbox{}\verb@          cout<<"string of length "<<(*iter).size()<<endl;@\\
\mbox{}\verb@          return false;@\\
\mbox{}\verb@        }@\\
\mbox{}\verb@      }@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  if(sorted[28].size() != 729)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    cout<<"Default case failed"<<endl;@\\
\mbox{}\verb@    return false;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  else@\\
\mbox{}\verb@  {/*check to make sure that every string here begins with a "{"@\\
\mbox{}\verb@  and that it does not contain an 'a' and is of length greater@\\
\mbox{}\verb@  than 2*/@\\
\mbox{}\verb@    for(iter = sorted[28].begin();iter != sorted[28].end();iter++)@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      if((*iter)[0] != (char)(123))@\\
\mbox{}\verb@      {@\\
\mbox{}\verb@        cout<<"String in begins with "<<(char)(123);@\\
\mbox{}\verb@        cout<<" container ";@\\
\mbox{}\verb@        cout<<"contains a string beginning with ";@\\
\mbox{}\verb@        cout<<(*iter)[0]<<endl;@\\
\mbox{}\verb@        return false;@\\
\mbox{}\verb@      }@\\
\mbox{}\verb@      /*also need to check that the string length of the string is@\\
\mbox{}\verb@      greater than 2*/@\\
\mbox{}\verb@      if((*iter).size() < 3)@\\
\mbox{}\verb@      {@\\
\mbox{}\verb@        cout<<"Begins letter """<<(char)(123)<<""" contains a ";@\\
\mbox{}\verb@        cout<<"string of length "<<(*iter).size()<<endl;@\\
\mbox{}\verb@        return false;@\\
\mbox{}\verb@      }@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  return true;@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@
\end{list}
\vspace{-2ex}
\end{flushleft}
\subsection{3-Priority Tests}
\subsubsection{3-Priority with Fall-Through}
\label{sec-code-test-3pt-f}
\begin{flushleft} \small \label{part118}
\verb@"priority3_fallthrough.cpp"@ {\footnotesize \hypertarget{231}{231} }$\equiv$
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@//priority3_fallthrough.cpp version 1.2@\\
\mbox{}\verb@#include <vector>@\\
\mbox{}\verb@#include <iostream>@\\
\mbox{}\verb@#include <fstream>@\\
\mbox{}\verb@#include <string>@\\
\mbox{}\verb@#include <ctype.h>@\\
\mbox{}\verb@#include "test_classes_fallthrough.hpp"@\\
\mbox{}\verb@#include "router.hpp"@\\
\mbox{}\verb@using std::cout;@\\
\mbox{}\verb@using std::endl;@\\
\mbox{}\verb@using std::vector;@\\
\mbox{}\verb@using std::back_inserter;@\\
\mbox{}\verb@using std::istream_iterator;@\\
\mbox{}\verb@using std::back_insert_iterator;@\\
\mbox{}\verb@using std::string;@\\
\mbox{}\verb@using std::cin;@\\
\mbox{}\verb@@\\
\mbox{}\verb@using gdfa::router;@\\
\mbox{}\verb@using gdfa::destination;@\\
\mbox{}\verb@@\\
\mbox{}\verb@bool validate(vector<string> sorted[]);@\\
\mbox{}\verb@@\\
\mbox{}\verb@typedef router<string>::priority_level plevel;@\\
\mbox{}\verb@@\\
\mbox{}\verb@template<typename InputIterator>@\\
\mbox{}\verb@bool testpriority(plevel p1,plevel p2,@\\
\mbox{}\verb@    plevel p3,InputIterator begin,InputIterator end)@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  router<string> r;@\\
\mbox{}\verb@  vector<string> sorted[30];//one for each letter, one for default@\\
\mbox{}\verb@  word_sorter<back_insert_iterator<vector<string> > > *dummy[26];@\\
\mbox{}\verb@  contains_letter<back_insert_iterator<vector<string> > >@\\
\mbox{}\verb@   contains_a(back_inserter(sorted[0]),'a');@\\
\mbox{}\verb@  r.add_destination(contains_a,p1);@\\
\mbox{}\verb@  length_counter<back_insert_iterator<vector<string> > >@\\
\mbox{}\verb@   length1(back_inserter(sorted[1]),1);@\\
\mbox{}\verb@  length_counter<back_insert_iterator<vector<string> > >@\\
\mbox{}\verb@   length2(back_inserter(sorted[2]),2);@\\
\mbox{}\verb@  r.add_destination(length1,p2);@\\
\mbox{}\verb@  r.add_destination(length2,p2);@\\
\mbox{}\verb@  for(int i = 0; i<26;i++)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    dummy[i] =@\\
\mbox{}\verb@     new word_sorter<back_insert_iterator<vector<string> > >@\\
\mbox{}\verb@     (back_inserter(sorted[i+3]),(char)(i + 97));@\\
\mbox{}\verb@    r.add_destination(*dummy[i],p3);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  my_default<back_insert_iterator<vector<string> > >@\\
\mbox{}\verb@   dflt(back_inserter(sorted[29]));@\\
\mbox{}\verb@  r.set_default(dflt);@\\
\mbox{}\verb@  r.distribute(begin,end);@\\
\mbox{}\verb@  return validate(sorted);@\\
\mbox{}\verb@}@\\
\mbox{}\verb@int main(int argc,char *argv[])@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  cout << "\n\n\nTest:  priority3_fallthrough.cpp\n\n"@\\
\mbox{}\verb@  <<"Test router with 3 priorities (allowing fall through)\n"@\\
\mbox{}\verb@  <<"***********************************************************"@\\
\mbox{}\verb@  <<"\n\n"@\\
\mbox{}\verb@  <<"Note: Fall through means that a destination\n"@\\
\mbox{}\verb@  <<"passes the element on to the next destination.\n\n"@\\
\mbox{}\verb@  <<"**********************************************\n\n"@\\
\mbox{}\verb@  <<"Results:\n\n";@\\
\mbox{}\verb@@\\
\mbox{}\verb@  router<string> r;@\\
\mbox{}\verb@  vector<string> sorted[30];//one for each letter, one for default@\\
\mbox{}\verb@  word_sorter<back_insert_iterator<vector<string> > > *dummy[26];@\\
\mbox{}\verb@  contains_letter<back_insert_iterator<vector<string> > >@\\
\mbox{}\verb@   contains_a(back_inserter(sorted[0]),'a');@\\
\mbox{}\verb@  r.add_destination(contains_a,router<string>::urgent_priority);@\\
\mbox{}\verb@  length_counter<back_insert_iterator<vector<string> > >@\\
\mbox{}\verb@   length1(back_inserter(sorted[1]),1);@\\
\mbox{}\verb@  length_counter<back_insert_iterator<vector<string> > >@\\
\mbox{}\verb@   length2(back_inserter(sorted[2]),2);@\\
\mbox{}\verb@  r.add_destination(length1,router<string>::high_priority);@\\
\mbox{}\verb@  r.add_destination(length2,router<string>::high_priority);@\\
\mbox{}\verb@  for(int i = 0; i<26;i++)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    dummy[i] =@\\
\mbox{}\verb@     new word_sorter<back_insert_iterator<vector<string> > >@\\
\mbox{}\verb@     (back_inserter(sorted[i+3]),(char)(i + 97));@\\
\mbox{}\verb@    r.add_destination(*dummy[i],router<string>::normal_priority);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  my_default<back_insert_iterator<vector<string> > >@\\
\mbox{}\verb@   dflt(back_inserter(sorted[29]));@\\
\mbox{}\verb@  r.set_default(dflt);@\\
\mbox{}\verb@  /*need to read all the input into a vector for storage so that@\\
\mbox{}\verb@  other priorities can be tested*/@\\
\mbox{}\verb@@\\
\mbox{}\verb@  //we want to create our own input for validation purposes@\\
\mbox{}\verb@  vector<string> storage_for_later;@\\
\mbox{}\verb@  createinputstring(storage_for_later);@\\
\mbox{}\verb@@\\
\mbox{}\verb@  //distribute@\\
\mbox{}\verb@  r.distribute(storage_for_later.begin(),storage_for_later.end());@\\
\mbox{}\verb@  cout<<"Results of testing urgent, high and normal priorities";@\\
\mbox{}\verb@  cout<<endl;@\\
\mbox{}\verb@  cout<<"words containing the letter (lowercase) a: ";@\\
\mbox{}\verb@  cout<<sorted[0].size()<<endl;@\\
\mbox{}\verb@  cout<<"words of length 1: "<<sorted[1].size()<<endl;@\\
\mbox{}\verb@  cout<<"words of length 2: "<<sorted[2].size()<<endl;@\\
\mbox{}\verb@  cout<<"counts for all other words, based on starting ";@\\
\mbox{}\verb@  cout<<"character, case insensitive"<<endl;@\\
\mbox{}\verb@  for(int i = 0;i<26;i++)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    cout<<(char)(i + 97)<<": "<<sorted[i + 3].size()<<endl;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  cout<<"Default: "<<sorted[29].size()<<endl;@\\
\mbox{}\verb@  if(validate(sorted))@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    cout<<"Passed test for urgent, high and normal priorities";@\\
\mbox{}\verb@    cout<<endl;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  else@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    cout<<"Failed test for urgent, high and normal priorities";@\\
\mbox{}\verb@    cout<<endl;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@@\\
\mbox{}\verb@  cout<<"Testing urgent, high and low priority"<<endl;@\\
\mbox{}\verb@  if(testpriority(router<string>::urgent_priority,@\\
\mbox{}\verb@     router<string>::high_priority,@\\
\mbox{}\verb@     router<string>::low_priority,storage_for_later.begin(),@\\
\mbox{}\verb@     storage_for_later.end()))@\\
\mbox{}\verb@    cout<<"Passed test for urgent, high and low priority"<<endl;@\\
\mbox{}\verb@  else@\\
\mbox{}\verb@    cout<<"Failed test for urgent, high and low priority"<<endl;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  cout<<"Testing urgent, normal and low priority"<<endl;@\\
\mbox{}\verb@  if(testpriority(router<string>::urgent_priority,@\\
\mbox{}\verb@     router<string>::normal_priority,@\\
\mbox{}\verb@     router<string>::low_priority,storage_for_later.begin(),@\\
\mbox{}\verb@     storage_for_later.end()))@\\
\mbox{}\verb@    cout<<"Passed test for urgent, normal and low priority"<<endl;@\\
\mbox{}\verb@  else@\\
\mbox{}\verb@    cout<<"Failed test for urgent, normal and low priority"<<endl;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  cout<<"Testing high, normal and low priority"<<endl;@\\
\mbox{}\verb@  if(testpriority(router<string>::high_priority,@\\
\mbox{}\verb@     router<string>::normal_priority,@\\
\mbox{}\verb@     router<string>::low_priority,storage_for_later.begin(),@\\
\mbox{}\verb@     storage_for_later.end()))@\\
\mbox{}\verb@    cout<<"Passed test for high, normal and low priority"<<endl;@\\
\mbox{}\verb@  else@\\
\mbox{}\verb@    cout<<"Failed test for high, normal and low priority"<<endl;@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@  cout<<"\n*************     END OF RESULTS     *************\n\n";@\\
\mbox{}\verb@@\\
\mbox{}\verb@  return 0;@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@\\
\mbox{}\verb@bool validate(vector<string> sorted[])@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  vector<string>::iterator iter;@\\
\mbox{}\verb@  if(sorted[0].size() != 4267)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    cout<<"Contains letter ""a"" failed"<<endl;@\\
\mbox{}\verb@    return false;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  else@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    /*check to make sure that each string in this container@\\
\mbox{}\verb@    contains an "a"*/@\\
\mbox{}\verb@    for(iter = sorted[0].begin();iter != sorted[0].end();iter++)@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      if(!((*iter).find("a")<(*iter).size()))@\\
\mbox{}\verb@      {@\\
\mbox{}\verb@        cout<<"String in ""a"" container does not contain ""a""";@\\
\mbox{}\verb@        cout<<endl;@\\
\mbox{}\verb@        return false;@\\
\mbox{}\verb@      }@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  if(sorted[1].size() != 19683)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    cout<<"Length 1 failed"<<endl;@\\
\mbox{}\verb@    return false;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  else@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    //check every string to make sure it is of length 1@\\
\mbox{}\verb@    for(iter = sorted[1].begin();iter != sorted[1].end();iter++)@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      if((*iter).size() != 1)@\\
\mbox{}\verb@      {@\\
\mbox{}\verb@        cout<<"String in length 1 container contains a string of ";@\\
\mbox{}\verb@        cout<<"not length 1"<<endl;@\\
\mbox{}\verb@        return false;@\\
\mbox{}\verb@      }@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  if(sorted[2].size() != 19683)  @\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    cout<<"Length 2 failed"<<endl;@\\
\mbox{}\verb@    return false;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  else@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    //check every string to make sure it is of length 2@\\
\mbox{}\verb@    for(iter = sorted[2].begin();iter != sorted[2].end();iter++)@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      if((*iter).size() != 2)@\\
\mbox{}\verb@      {@\\
\mbox{}\verb@        cout<<"String in length 2 container contains a string of ";@\\
\mbox{}\verb@        cout<<"not length 2"<<endl;@\\
\mbox{}\verb@        return false;@\\
\mbox{}\verb@      }@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  for(int i = 3;i<29;i++)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    if(sorted[i].size() != 2187)@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      cout<<"Begins letter """<<(char)(i+94)<<""" failed"<<endl;@\\
\mbox{}\verb@      return false;@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@    else@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      /*check each string to make sure it starts with the correct@\\
\mbox{}\verb@      letter*/@\\
\mbox{}\verb@      for(iter = sorted[i].begin();iter != sorted[i].end();iter++)@\\
\mbox{}\verb@      {@\\
\mbox{}\verb@        if((*iter)[0] != (char)(i+94))@\\
\mbox{}\verb@        {@\\
\mbox{}\verb@          cout<<"String in begins with "<<(char)(i+94);@\\
\mbox{}\verb@          cout<<" container ";@\\
\mbox{}\verb@          cout<<"contains a string beginning with ";@\\
\mbox{}\verb@          cout<<(*iter)[0]<<endl;@\\
\mbox{}\verb@          return false;@\\
\mbox{}\verb@        }@\\
\mbox{}\verb@      }@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  if(sorted[29].size() != 59049)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    cout<<"Default case failed"<<endl;@\\
\mbox{}\verb@    return false;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  return true;@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@
\end{list}
\vspace{-2ex}
\end{flushleft}
\subsubsection{3-Priority without Fall-Through}
\label{sec-code-test-3pt-n}
\begin{flushleft} \small \label{part119}
\verb@"priority3_nofallthrough.cpp"@ {\footnotesize \hypertarget{236}{236} }$\equiv$
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@//priority3_nofallthrough.cpp version 1.2@\\
\mbox{}\verb@#include <vector>@\\
\mbox{}\verb@#include <iostream>@\\
\mbox{}\verb@#include <fstream>@\\
\mbox{}\verb@#include <string>@\\
\mbox{}\verb@#include <ctype.h>@\\
\mbox{}\verb@#include "test_classes.hpp"@\\
\mbox{}\verb@#include "router.hpp"@\\
\mbox{}\verb@using std::cout;@\\
\mbox{}\verb@using std::endl;@\\
\mbox{}\verb@using std::vector;@\\
\mbox{}\verb@using std::back_inserter;@\\
\mbox{}\verb@using std::istream_iterator;@\\
\mbox{}\verb@using std::back_insert_iterator;@\\
\mbox{}\verb@using std::string;@\\
\mbox{}\verb@using std::cin;@\\
\mbox{}\verb@@\\
\mbox{}\verb@using gdfa::router;@\\
\mbox{}\verb@using gdfa::destination;@\\
\mbox{}\verb@@\\
\mbox{}\verb@bool validate(vector<string> sorted[]);@\\
\mbox{}\verb@typedef router<string>::priority_level plevel;@\\
\mbox{}\verb@@\\
\mbox{}\verb@template<typename InputIterator>@\\
\mbox{}\verb@bool testpriority(plevel p1,plevel p2,@\\
\mbox{}\verb@          plevel p3,InputIterator begin,InputIterator end)@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  router<string> r;@\\
\mbox{}\verb@  vector<string> sorted[30];//one for each letter, one for default@\\
\mbox{}\verb@  word_sorter<back_insert_iterator<vector<string> > > *dummy[26];@\\
\mbox{}\verb@  contains_letter<back_insert_iterator<vector<string> > >@\\
\mbox{}\verb@   contains_a(back_inserter(sorted[0]),'a');@\\
\mbox{}\verb@  r.add_destination(contains_a,p1);@\\
\mbox{}\verb@  length_counter<back_insert_iterator<vector<string> > >@\\
\mbox{}\verb@   length1(back_inserter(sorted[1]),1);@\\
\mbox{}\verb@  length_counter<back_insert_iterator<vector<string> > >@\\
\mbox{}\verb@   length2(back_inserter(sorted[2]),2);@\\
\mbox{}\verb@  r.add_destination(length1,p2);@\\
\mbox{}\verb@  r.add_destination(length2,p2);@\\
\mbox{}\verb@  for(int i = 0; i<26;i++)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    dummy[i] =@\\
\mbox{}\verb@     new word_sorter<back_insert_iterator<vector<string> > >@\\
\mbox{}\verb@     (back_inserter(sorted[i+3]),(char)(i + 97));@\\
\mbox{}\verb@    r.add_destination(*dummy[i],p3);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  my_default<back_insert_iterator<vector<string> > >@\\
\mbox{}\verb@   dflt(back_inserter(sorted[29]));@\\
\mbox{}\verb@  r.set_default(dflt);@\\
\mbox{}\verb@  r.distribute(begin,end);@\\
\mbox{}\verb@  return validate(sorted);@\\
\mbox{}\verb@}@\\
\mbox{}\verb@int main(int argc,char *argv[])@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  cout << "\n\n\nTest:  priority3_nofallthrough.cpp\n\n"@\\
\mbox{}\verb@    << "Test router with 3 priorities (No fall through)\n"@\\
\mbox{}\verb@    << "***********************************************\n\n"@\\
\mbox{}\verb@    << "(Note: Fall through means that a destination\n"@\\
\mbox{}\verb@    << "passes the element on to the next destination.\n\n"@\\
\mbox{}\verb@    << "**********************************************\n\n"@\\
\mbox{}\verb@    << "Results:\n\n";@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@  router<string> r;@\\
\mbox{}\verb@  vector<string> sorted[30];//one for each letter, one for default@\\
\mbox{}\verb@  word_sorter<back_insert_iterator<vector<string> > > *dummy[26];@\\
\mbox{}\verb@  contains_letter<back_insert_iterator<vector<string> > >@\\
\mbox{}\verb@   contains_a(back_inserter(sorted[0]),'a');@\\
\mbox{}\verb@  r.add_destination(contains_a,router<string>::urgent_priority);@\\
\mbox{}\verb@  length_counter<back_insert_iterator<vector<string> > >@\\
\mbox{}\verb@   length1(back_inserter(sorted[1]),1);@\\
\mbox{}\verb@  length_counter<back_insert_iterator<vector<string> > >@\\
\mbox{}\verb@   length2(back_inserter(sorted[2]),2);@\\
\mbox{}\verb@  r.add_destination(length1,router<string>::high_priority);@\\
\mbox{}\verb@  r.add_destination(length2,router<string>::high_priority);@\\
\mbox{}\verb@  for(int i = 0; i<26;i++)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    dummy[i] =@\\
\mbox{}\verb@     new word_sorter<back_insert_iterator<vector<string> > >@\\
\mbox{}\verb@     (back_inserter(sorted[i+3]),(char)(i + 97));@\\
\mbox{}\verb@    r.add_destination(*dummy[i],router<string>::normal_priority);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  my_default<back_insert_iterator<vector<string> > >@\\
\mbox{}\verb@   dflt(back_inserter(sorted[29]));@\\
\mbox{}\verb@  r.set_default(dflt);@\\
\mbox{}\verb@@\\
\mbox{}\verb@  //we want to create our own input for validation purposes@\\
\mbox{}\verb@  vector<string> storage_for_later;@\\
\mbox{}\verb@  createinputstring(storage_for_later);@\\
\mbox{}\verb@@\\
\mbox{}\verb@  //distribute@\\
\mbox{}\verb@  r.distribute(storage_for_later.begin(),storage_for_later.end());@\\
\mbox{}\verb@  cout<<"Results of testing urgent, high and normal priorities";@\\
\mbox{}\verb@  cout<<endl;@\\
\mbox{}\verb@  cout<<"words containing the letter (lowercase) a: ";@\\
\mbox{}\verb@  cout<<sorted[0].size()<<endl;@\\
\mbox{}\verb@  cout<<"words of length 1: "<<sorted[1].size()<<endl;@\\
\mbox{}\verb@  cout<<"words of length 2: "<<sorted[2].size()<<endl;@\\
\mbox{}\verb@  cout<<"counts for all other words, based on starting ";@\\
\mbox{}\verb@  cout<<"character, case insensitive"<<endl;@\\
\mbox{}\verb@  for(int i = 0;i<26;i++)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    cout<<(char)(i + 97)<<": "<<sorted[i + 3].size()<<endl;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  cout<<"Default: "<<sorted[29].size()<<endl;@\\
\mbox{}\verb@  if(validate(sorted))@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    cout<<"Passed test for urgent, high and normal priorities";@\\
\mbox{}\verb@    cout<<endl;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  else@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    cout<<"Failed test for urgent, high and normal priorities";@\\
\mbox{}\verb@    cout<<endl;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@  cout<<"Testing urgent, high and low priority"<<endl;@\\
\mbox{}\verb@  if(testpriority(router<string>::urgent_priority,@\\
\mbox{}\verb@     router<string>::high_priority,@\\
\mbox{}\verb@     router<string>::low_priority,storage_for_later.begin(),@\\
\mbox{}\verb@     storage_for_later.end()))@\\
\mbox{}\verb@    cout<<"Passed test for urgent high and low priority"<<endl;@\\
\mbox{}\verb@  else@\\
\mbox{}\verb@    cout<<"Failed test for urgent high and low priority"<<endl;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  cout<<"Testing urgent, normal and low priority"<<endl;@\\
\mbox{}\verb@  if(testpriority(router<string>::urgent_priority,@\\
\mbox{}\verb@     router<string>::normal_priority,@\\
\mbox{}\verb@     router<string>::low_priority,storage_for_later.begin(),@\\
\mbox{}\verb@     storage_for_later.end()))@\\
\mbox{}\verb@    cout<<"Passed test for urgent, normal and low priority"<<endl;@\\
\mbox{}\verb@  else@\\
\mbox{}\verb@    cout<<"Failed test for urgent, normal and low priority"<<endl;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  cout<<"Testing high, normal and low priority"<<endl;@\\
\mbox{}\verb@  if(testpriority(router<string>::high_priority,@\\
\mbox{}\verb@     router<string>::normal_priority,@\\
\mbox{}\verb@     router<string>::low_priority,storage_for_later.begin(),@\\
\mbox{}\verb@     storage_for_later.end()))@\\
\mbox{}\verb@    cout<<"Passed test for high, normal and low priority"<<endl;@\\
\mbox{}\verb@  else@\\
\mbox{}\verb@    cout<<"Failed test for high, normal and low priority"<<endl;@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@  cout<<"\n*************     END OF RESULTS     *************\n\n";@\\
\mbox{}\verb@@\\
\mbox{}\verb@  return 0;@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@\\
\mbox{}\verb@bool validate(vector<string> sorted[])@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  vector<string>::iterator iter;@\\
\mbox{}\verb@  if(sorted[0].size() != 4267)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    cout<<"Contains letter ""a"" failed"<<endl;@\\
\mbox{}\verb@    return false;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  else@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    /*check to make sure that each string in this container@\\
\mbox{}\verb@    contains an "a"*/@\\
\mbox{}\verb@    for(iter = sorted[0].begin();iter != sorted[0].end();iter++)@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      if(!((*iter).find("a")<(*iter).size()))@\\
\mbox{}\verb@      {@\\
\mbox{}\verb@        cout<<"String in ""a"" container does not contain ""a""";@\\
\mbox{}\verb@        cout<<endl;@\\
\mbox{}\verb@        return false;@\\
\mbox{}\verb@      }@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  if(sorted[1].size() != 18954)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    cout<<"Length 1 failed"<<endl;@\\
\mbox{}\verb@    return false;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  else@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    //check every string to make sure it is of length 1@\\
\mbox{}\verb@    for(iter = sorted[1].begin();iter != sorted[1].end();iter++)@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      if((*iter).size() != 1)@\\
\mbox{}\verb@      {@\\
\mbox{}\verb@        cout<<"String in length 1 container contains a string of ";@\\
\mbox{}\verb@        cout<<"not length 1"<<endl;@\\
\mbox{}\verb@        return false;@\\
\mbox{}\verb@      }@\\
\mbox{}\verb@      /*also need to check to make sure that there are no 'a's in@\\
\mbox{}\verb@      this contianer*/@\\
\mbox{}\verb@      if((*iter).find("a")<(*iter).size())@\\
\mbox{}\verb@      {@\\
\mbox{}\verb@        cout<<"String in length 1 container contains an ""a""";@\\
\mbox{}\verb@        cout<<endl;@\\
\mbox{}\verb@        return false;@\\
\mbox{}\verb@      }@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  if(sorted[2].size() != 18252)  @\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    cout<<"Length 2 failed"<<endl;@\\
\mbox{}\verb@    return false;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  else@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    //check every string to make sure it is of length 2@\\
\mbox{}\verb@    for(iter = sorted[2].begin();iter != sorted[2].end();iter++)@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      if((*iter).size() != 2)@\\
\mbox{}\verb@      {@\\
\mbox{}\verb@        cout<<"String in length 2 container contains a string of ";@\\
\mbox{}\verb@        cout<<"not length 2"<<endl;@\\
\mbox{}\verb@        return false;@\\
\mbox{}\verb@      }@\\
\mbox{}\verb@      /*also need to check to make sure that there are no 'a's in@\\
\mbox{}\verb@      this contianer*/@\\
\mbox{}\verb@      if((*iter).find("a")<(*iter).size())@\\
\mbox{}\verb@      {@\\
\mbox{}\verb@        cout<<"String in length 2 container contains an ""a""";@\\
\mbox{}\verb@        cout<<endl;@\\
\mbox{}\verb@        return false;@\\
\mbox{}\verb@      }@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  if(sorted[3].size() != 0)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    /*there are strings in the container for begins with "a" and@\\
\mbox{}\verb@    there shouldn't be*/@\\
\mbox{}\verb@    cout<<"Begins letter """<<(char)(97)<<""" failed"<<endl;@\\
\mbox{}\verb@    return false;@\\
\mbox{}\verb@  }    @\\
\mbox{}\verb@  for(int i = 4;i<29;i++)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    if(sorted[i].size() != 676)@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      cout<<"Begins letter """<<(char)(i+94)<<""" failed"<<endl;@\\
\mbox{}\verb@      return false;@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@    else@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      /*check each string to make sure it starts with the correct@\\
\mbox{}\verb@      letter*/@\\
\mbox{}\verb@      for(iter = sorted[i].begin();iter != sorted[i].end();iter++)@\\
\mbox{}\verb@      {@\\
\mbox{}\verb@        if((*iter)[0] != (char)(i+94))@\\
\mbox{}\verb@        {@\\
\mbox{}\verb@          cout<<"String in begins with "<<(char)(i+94);@\\
\mbox{}\verb@          cout<<" container ";@\\
\mbox{}\verb@          cout<<"contains a string beginning with ";@\\
\mbox{}\verb@          cout<<(*iter)[0]<<endl;@\\
\mbox{}\verb@          return false;@\\
\mbox{}\verb@        }@\\
\mbox{}\verb@        /*also need to check to make sure that there are no 'a's in@\\
\mbox{}\verb@        this container*/@\\
\mbox{}\verb@        if((*iter).find("a")<(*iter).size())@\\
\mbox{}\verb@        {@\\
\mbox{}\verb@          cout<<"Begins letter """<<(char)(i+94);@\\
\mbox{}\verb@          cout<<""" contains the ";@\\
\mbox{}\verb@          cout<<"letter 'a'"<<endl;@\\
\mbox{}\verb@          return false;@\\
\mbox{}\verb@        }@\\
\mbox{}\verb@        /*also need to check that the string length of the string@\\
\mbox{}\verb@        is greater than 2*/@\\
\mbox{}\verb@        if((*iter).size() < 3)@\\
\mbox{}\verb@        {@\\
\mbox{}\verb@          cout<<"Begins letter """<<(char)(i+94)<<""" contains ";@\\
\mbox{}\verb@          cout<<"a string of length "<<(*iter).size()<<endl;@\\
\mbox{}\verb@          return false;@\\
\mbox{}\verb@        }@\\
\mbox{}\verb@      }@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  if(sorted[29].size() != 676)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    cout<<"Default case failed"<<endl;@\\
\mbox{}\verb@    return false;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  else@\\
\mbox{}\verb@  {/*check to make sure that every string here begins with a "{"@\\
\mbox{}\verb@  and that it does not contain an 'a' and is*/@\\
\mbox{}\verb@    //of length greater than 2@\\
\mbox{}\verb@    for(iter = sorted[29].begin();iter != sorted[29].end();iter++)@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      if((*iter)[0] != (char)(123))@\\
\mbox{}\verb@      {@\\
\mbox{}\verb@        cout<<"String in begins with "<<(char)(123);@\\
\mbox{}\verb@        cout<<" container contains a string beginning with ";@\\
\mbox{}\verb@        cout<<(*iter)[0]<<endl;@\\
\mbox{}\verb@        return false;@\\
\mbox{}\verb@      }@\\
\mbox{}\verb@      /*also need to check to make sure that there are no 'a's in@\\
\mbox{}\verb@      this container*/@\\
\mbox{}\verb@      if((*iter).find("a")<(*iter).size())@\\
\mbox{}\verb@      {@\\
\mbox{}\verb@        cout<<"Begins letter """<<(char)(123);@\\
\mbox{}\verb@        cout<<""" contains the letter 'a'"<<endl;@\\
\mbox{}\verb@        return false;@\\
\mbox{}\verb@      }@\\
\mbox{}\verb@      /*also need to check that the string length of the string is@\\
\mbox{}\verb@      greater than 2*/@\\
\mbox{}\verb@      if((*iter).size() < 3)@\\
\mbox{}\verb@      {@\\
\mbox{}\verb@        cout<<"Begins letter """<<(char)(123);@\\
\mbox{}\verb@        cout<<""" contains a string ";@\\
\mbox{}\verb@        cout<<"of length "<<(*iter).size()<<endl;@\\
\mbox{}\verb@        return false;@\\
\mbox{}\verb@      }@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  return true;@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@
\end{list}
\vspace{-2ex}
\end{flushleft}
\subsection{4-Priority Tests}
\subsubsection{4-Priority with Fall-Through}
\label{sec-code-test-4pt-f}
\begin{flushleft} \small \label{part120}
\verb@"priority4_fallthrough.cpp"@ {\footnotesize \hypertarget{243}{243} }$\equiv$
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@//priority4_fallthrough.cpp version 1.0@\\
\mbox{}\verb@#include <vector>@\\
\mbox{}\verb@#include <iostream>@\\
\mbox{}\verb@#include <fstream>@\\
\mbox{}\verb@#include <string>@\\
\mbox{}\verb@#include <ctype.h>@\\
\mbox{}\verb@#include "test_classes_fallthrough.hpp"@\\
\mbox{}\verb@#include "router.hpp"@\\
\mbox{}\verb@#include "validate.hpp"@\\
\mbox{}\verb@using std::cout;@\\
\mbox{}\verb@using std::endl;@\\
\mbox{}\verb@using std::vector;@\\
\mbox{}\verb@using std::back_inserter;@\\
\mbox{}\verb@using std::istream_iterator;@\\
\mbox{}\verb@using std::back_insert_iterator;@\\
\mbox{}\verb@using std::string;@\\
\mbox{}\verb@using std::cin;@\\
\mbox{}\verb@@\\
\mbox{}\verb@using gdfa::router;@\\
\mbox{}\verb@using gdfa::destination;@\\
\mbox{}\verb@@\\
\mbox{}\verb@bool validate(vector<string> sorted[]);@\\
\mbox{}\verb@@\\
\mbox{}\verb@typedef router<string>::priority_level plevel;@\\
\mbox{}\verb@@\\
\mbox{}\verb@int main(int argc,char *argv[])@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  cout << "\n\n\nTest:  priority4_fallthrough.cpp\n\n"@\\
\mbox{}\verb@  <<"Test router with 4 priorities (allowing fall through)\n"@\\
\mbox{}\verb@  <<"***********************************************************"@\\
\mbox{}\verb@  <<"\n\n"@\\
\mbox{}\verb@  <<"Note: Fall through means that a destination\n"@\\
\mbox{}\verb@  <<"passes the element on to the next destination.\n\n"@\\
\mbox{}\verb@  <<"**********************************************\n\n"@\\
\mbox{}\verb@  <<"Results:\n\n";@\\
\mbox{}\verb@@\\
\mbox{}\verb@  router<string> r;@\\
\mbox{}\verb@  vector<string> sorted[31];//one for each letter, one for default@\\
\mbox{}\verb@  word_sorter<back_insert_iterator<vector<string> > > *dummy[26];@\\
\mbox{}\verb@@\\
\mbox{}\verb@  contains_string<back_insert_iterator<vector<string> > >@\\
\mbox{}\verb@   contains_ea(back_inserter(sorted[0]),"ea");@\\
\mbox{}\verb@  r.add_destination(contains_ea,router<string>::urgent_priority);@\\
\mbox{}\verb@@\\
\mbox{}\verb@  contains_letter<back_insert_iterator<vector<string> > >@\\
\mbox{}\verb@   contains_a(back_inserter(sorted[1]),'a');@\\
\mbox{}\verb@  r.add_destination(contains_a,router<string>::high_priority);@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  @\\
\mbox{}\verb@  length_counter<back_insert_iterator<vector<string> > >@\\
\mbox{}\verb@   length1(back_inserter(sorted[2]),1);@\\
\mbox{}\verb@  length_counter<back_insert_iterator<vector<string> > >@\\
\mbox{}\verb@   length2(back_inserter(sorted[3]),2);@\\
\mbox{}\verb@  r.add_destination(length1,router<string>::normal_priority);@\\
\mbox{}\verb@  r.add_destination(length2,router<string>::normal_priority);@\\
\mbox{}\verb@  for(int i = 0; i<26;i++)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    dummy[i] =@\\
\mbox{}\verb@     new word_sorter<back_insert_iterator<vector<string> > >@\\
\mbox{}\verb@     (back_inserter(sorted[i+4]),(char)(i + 97));@\\
\mbox{}\verb@    r.add_destination(*dummy[i],router<string>::low_priority);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  my_default<back_insert_iterator<vector<string> > >@\\
\mbox{}\verb@   dflt(back_inserter(sorted[30]));@\\
\mbox{}\verb@  r.set_default(dflt);@\\
\mbox{}\verb@  /*need to read all the input into a vector for storage so that@\\
\mbox{}\verb@  other priorities can be tested*/@\\
\mbox{}\verb@  vector<string> storage_for_later;@\\
\mbox{}\verb@  createinputstring(storage_for_later);@\\
\mbox{}\verb@  //distribute@\\
\mbox{}\verb@  r.distribute(storage_for_later.begin(),storage_for_later.end());@\\
\mbox{}\verb@  cout<<"Results of testing urgent, high, normal and low ";@\\
\mbox{}\verb@  cout<<"priorities"<<endl;@\\
\mbox{}\verb@  cout<<"Words containing the string \"ea\": ";@\\
\mbox{}\verb@  cout<<sorted[0].size()<<endl;@\\
\mbox{}\verb@  cout<<"words containing the letter (lowercase) a: ";@\\
\mbox{}\verb@  cout<<sorted[1].size()<<endl;@\\
\mbox{}\verb@  cout<<"words of length 1: "<<sorted[2].size()<<endl;@\\
\mbox{}\verb@  cout<<"words of length 2: "<<sorted[3].size()<<endl;@\\
\mbox{}\verb@  cout<<"counts for all other words, based on starting ";@\\
\mbox{}\verb@  cout<<"character, case insensitive"<<endl;@\\
\mbox{}\verb@  for(int i = 0;i<26;i++)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    cout<<(char)(i + 97)<<": "<<sorted[i + 4].size()<<endl;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  cout<<"Default: "<<sorted[30].size()<<endl;@\\
\mbox{}\verb@  if(validate(sorted))@\\
\mbox{}\verb@    cout<<"Passed Validation Test"<<endl;@\\
\mbox{}\verb@  else@\\
\mbox{}\verb@    cout<<"Failed Validation Test"<<endl;@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@  cout<<"\n*************     END OF RESULTS     *************\n\n";@\\
\mbox{}\verb@@\\
\mbox{}\verb@  return 0;@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@\\
\mbox{}\verb@bool validate(vector<string> sorted[])@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  vector<string>::iterator iter;@\\
\mbox{}\verb@  if(sorted[0].size() != 81)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    cout<<"Contains ""ae"" failed"<<endl;@\\
\mbox{}\verb@    return false;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  else@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    /*check to make sure that each string in this container@\\
\mbox{}\verb@    contains "ea"*/@\\
\mbox{}\verb@    for(iter = sorted[0].begin();iter != sorted[0].end();iter++)@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      if(!((*iter).find("ea")<(*iter).size()))@\\
\mbox{}\verb@      {@\\
\mbox{}\verb@        cout<<"String in ""ea"" container does not contain ""ea""";@\\
\mbox{}\verb@        cout<<endl;@\\
\mbox{}\verb@        return false;@\\
\mbox{}\verb@      }@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  if(sorted[1].size() != 4267)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    cout<<"Contains letter ""a"" failed"<<endl;@\\
\mbox{}\verb@    return false;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  else@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    /*check to make sure that each string in this container@\\
\mbox{}\verb@    contains an "a"*/@\\
\mbox{}\verb@    for(iter = sorted[1].begin();iter != sorted[1].end();iter++)@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      if(!((*iter).find("a")<(*iter).size()))@\\
\mbox{}\verb@      {@\\
\mbox{}\verb@        cout<<"String in ""a"" container does not contain ""a""";@\\
\mbox{}\verb@        cout<<endl;@\\
\mbox{}\verb@        return false;@\\
\mbox{}\verb@      }@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  if(sorted[2].size() != 19683)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    cout<<"Length 1 failed"<<endl;@\\
\mbox{}\verb@    return false;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  else@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    //check every string to make sure it is of length 1@\\
\mbox{}\verb@    for(iter = sorted[2].begin();iter != sorted[2].end();iter++)@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      if((*iter).size() != 1)@\\
\mbox{}\verb@      {@\\
\mbox{}\verb@        cout<<"String in length 1 container contains a string of ";@\\
\mbox{}\verb@        cout<<"not length 1"<<endl;@\\
\mbox{}\verb@        return false;@\\
\mbox{}\verb@      }@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  if(sorted[3].size() != 19683)  @\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    cout<<"Length 2 failed"<<endl;@\\
\mbox{}\verb@    return false;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  else@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    //check every string to make sure it is of length 2@\\
\mbox{}\verb@    for(iter = sorted[3].begin();iter != sorted[3].end();iter++)@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      if((*iter).size() != 2)@\\
\mbox{}\verb@      {@\\
\mbox{}\verb@        cout<<"String in length 2 container contains a string of ";@\\
\mbox{}\verb@        cout<<"not length 2"<<endl;@\\
\mbox{}\verb@        return false;@\\
\mbox{}\verb@      }@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  for(int i = 4;i<30;i++)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    if(sorted[i].size() != 2187)@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      cout<<"Begins letter """<<(char)(i+93)<<""" failed"<<endl;@\\
\mbox{}\verb@      return false;@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@    else@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      /*check each string to make sure it starts with the correct@\\
\mbox{}\verb@      letter*/@\\
\mbox{}\verb@      for(iter = sorted[i].begin();iter != sorted[i].end();iter++)@\\
\mbox{}\verb@      {@\\
\mbox{}\verb@        if((*iter)[0] != (char)(i+93))@\\
\mbox{}\verb@        {@\\
\mbox{}\verb@          cout<<"String in begins with "<<(char)(i+93);@\\
\mbox{}\verb@          cout<<" container ";@\\
\mbox{}\verb@          cout<<"contains a string beginning with ";@\\
\mbox{}\verb@          cout<<(*iter)[0]<<endl;@\\
\mbox{}\verb@          return false;@\\
\mbox{}\verb@        }@\\
\mbox{}\verb@      }@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  //everything should be caught by the default case@\\
\mbox{}\verb@  if(sorted[30].size() != 59049)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    cout<<"Default case failed"<<endl;@\\
\mbox{}\verb@    return false;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  return true;@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@
\end{list}
\vspace{-2ex}
\end{flushleft}
\subsubsection{4-Priority without Fall-Through}
\label{sec-code-test-4pt-n}
\begin{flushleft} \small \label{part121}
\verb@"priority4_nofallthrough.cpp"@ {\footnotesize \hypertarget{247}{247} }$\equiv$
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@//priority4_nofallthrough.cpp version 1.0@\\
\mbox{}\verb@#include <vector>@\\
\mbox{}\verb@#include <iostream>@\\
\mbox{}\verb@#include <fstream>@\\
\mbox{}\verb@#include <string>@\\
\mbox{}\verb@#include <ctype.h>@\\
\mbox{}\verb@#include "test_classes.hpp"@\\
\mbox{}\verb@#include "router.hpp"@\\
\mbox{}\verb@#include "validate.hpp"@\\
\mbox{}\verb@using std::cout;@\\
\mbox{}\verb@using std::endl;@\\
\mbox{}\verb@using std::vector;@\\
\mbox{}\verb@using std::back_inserter;@\\
\mbox{}\verb@using std::istream_iterator;@\\
\mbox{}\verb@using std::back_insert_iterator;@\\
\mbox{}\verb@using std::string;@\\
\mbox{}\verb@using std::cin;@\\
\mbox{}\verb@@\\
\mbox{}\verb@using gdfa::router;@\\
\mbox{}\verb@using gdfa::destination;@\\
\mbox{}\verb@@\\
\mbox{}\verb@bool validate(vector<string> sorted[]);@\\
\mbox{}\verb@@\\
\mbox{}\verb@typedef router<string>::priority_level plevel;@\\
\mbox{}\verb@@\\
\mbox{}\verb@int main(int argc,char *argv[])@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  cout << "\n\n\nTest:  priority4_nofallthrough.cpp\n\n"@\\
\mbox{}\verb@     << "Test router with 4 priorities (No fall through)\n"@\\
\mbox{}\verb@     << "***********************************************\n\n"@\\
\mbox{}\verb@     << "(Note: Fall through means that a destination\n"@\\
\mbox{}\verb@     << "passes the element on to the next destination.\n\n"@\\
\mbox{}\verb@     << "**********************************************\n\n"@\\
\mbox{}\verb@     << "Results:\n\n";@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@  router<string> r;@\\
\mbox{}\verb@  vector<string> sorted[31];//one for each letter, one for default@\\
\mbox{}\verb@  word_sorter<back_insert_iterator<vector<string> > > *dummy[26];@\\
\mbox{}\verb@@\\
\mbox{}\verb@  contains_string<back_insert_iterator<vector<string> > >@\\
\mbox{}\verb@   contains_ea(back_inserter(sorted[0]),"ea");@\\
\mbox{}\verb@  r.add_destination(contains_ea,router<string>::urgent_priority);@\\
\mbox{}\verb@@\\
\mbox{}\verb@  contains_letter<back_insert_iterator<vector<string> > >@\\
\mbox{}\verb@   contains_a(back_inserter(sorted[1]),'a');@\\
\mbox{}\verb@  r.add_destination(contains_a,router<string>::high_priority);@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  @\\
\mbox{}\verb@  length_counter<back_insert_iterator<vector<string> > >@\\
\mbox{}\verb@   length1(back_inserter(sorted[2]),1);@\\
\mbox{}\verb@  length_counter<back_insert_iterator<vector<string> > >@\\
\mbox{}\verb@   length2(back_inserter(sorted[3]),2);@\\
\mbox{}\verb@  r.add_destination(length1,router<string>::normal_priority);@\\
\mbox{}\verb@  r.add_destination(length2,router<string>::normal_priority);@\\
\mbox{}\verb@  for(int i = 0; i<26;i++)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    dummy[i] =@\\
\mbox{}\verb@     new word_sorter<back_insert_iterator<vector<string> > >@\\
\mbox{}\verb@     (back_inserter(sorted[i+4]),(char)(i + 97));@\\
\mbox{}\verb@    r.add_destination(*dummy[i],router<string>::low_priority);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  my_default<back_insert_iterator<vector<string> > >@\\
\mbox{}\verb@   dflt(back_inserter(sorted[30]));@\\
\mbox{}\verb@  r.set_default(dflt);@\\
\mbox{}\verb@  /*need to read all the input into a vector for storage so that@\\
\mbox{}\verb@  other priorities can be tested*/@\\
\mbox{}\verb@  vector<string> storage_for_later;@\\
\mbox{}\verb@  createinputstring(storage_for_later);@\\
\mbox{}\verb@  //distribute@\\
\mbox{}\verb@  r.distribute(storage_for_later.begin(),storage_for_later.end());@\\
\mbox{}\verb@  cout<<"Results of testing urgent, high, normal and low ";@\\
\mbox{}\verb@  cout<<"priorities"<<endl;@\\
\mbox{}\verb@  cout<<"Words containing the string \"ea\": ";@\\
\mbox{}\verb@  cout<<sorted[0].size()<<endl;@\\
\mbox{}\verb@  cout<<"words containing the letter (lowercase) a: ";@\\
\mbox{}\verb@  cout<<sorted[1].size()<<endl;@\\
\mbox{}\verb@  cout<<"words of length 1: "<<sorted[2].size()<<endl;@\\
\mbox{}\verb@  cout<<"words of length 2: "<<sorted[3].size()<<endl;@\\
\mbox{}\verb@  cout<<"counts for all other words, based on starting ";@\\
\mbox{}\verb@  cout<<"character, case insensitive"<<endl;@\\
\mbox{}\verb@  for(int i = 0;i<26;i++)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    cout<<(char)(i + 97)<<": "<<sorted[i + 4].size()<<endl;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  cout<<"Default: "<<sorted[30].size()<<endl;@\\
\mbox{}\verb@  if(validate(sorted))@\\
\mbox{}\verb@    cout<<"Passed Validation Test"<<endl;@\\
\mbox{}\verb@  else@\\
\mbox{}\verb@    cout<<"Failed Validation Test"<<endl;@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@  cout<<"\n*************     END OF RESULTS     *************\n\n";@\\
\mbox{}\verb@@\\
\mbox{}\verb@  return 0;@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@\\
\mbox{}\verb@bool validate(vector<string> sorted[])@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  vector<string>::iterator iter;@\\
\mbox{}\verb@  if(sorted[0].size() != 81)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    cout<<"Contains ""ae"" failed"<<endl;@\\
\mbox{}\verb@    return false;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  else@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    /*check to make sure that each string in this container@\\
\mbox{}\verb@    contains "ea"*/@\\
\mbox{}\verb@    for(iter = sorted[0].begin();iter != sorted[0].end();iter++)@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      if(!((*iter).find("ea")<(*iter).size()))@\\
\mbox{}\verb@      {@\\
\mbox{}\verb@        cout<<"String in ""ea"" container does not contain ""ea""";@\\
\mbox{}\verb@        cout<<endl;@\\
\mbox{}\verb@        return false;@\\
\mbox{}\verb@      }@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  if(sorted[1].size() != 4186)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    cout<<"Contains letter ""a"" failed"<<endl;@\\
\mbox{}\verb@    return false;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  else@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    /*check to make sure that each string in this container@\\
\mbox{}\verb@    contains an "a"*/@\\
\mbox{}\verb@    for(iter = sorted[1].begin();iter != sorted[1].end();iter++)@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      if(!((*iter).find("a")<(*iter).size()))@\\
\mbox{}\verb@      {@\\
\mbox{}\verb@        cout<<"String in ""a"" container does not contain ""a""";@\\
\mbox{}\verb@        cout<<endl;@\\
\mbox{}\verb@        return false;@\\
\mbox{}\verb@      }@\\
\mbox{}\verb@      //also need to check that no string contains "ea"@\\
\mbox{}\verb@      if((*iter).find("ea")<(*iter).size())@\\
\mbox{}\verb@      {@\\
\mbox{}\verb@        cout<<"String in ""a"" container contains an ""ea"""<<endl;@\\
\mbox{}\verb@        return false;@\\
\mbox{}\verb@      }@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  if(sorted[2].size() != 18954)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    cout<<"Length 1 failed"<<endl;@\\
\mbox{}\verb@    return false;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  else@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    //check every string to make sure it is of length 1@\\
\mbox{}\verb@    for(iter = sorted[2].begin();iter != sorted[2].end();iter++)@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      if((*iter).size() != 1)@\\
\mbox{}\verb@      {@\\
\mbox{}\verb@        cout<<"String in length 1 container contains a string of ";@\\
\mbox{}\verb@        cout<<"not length 1"<<endl;@\\
\mbox{}\verb@        return false;@\\
\mbox{}\verb@      }@\\
\mbox{}\verb@      /*also need to check to make sure that there are no 'a's in@\\
\mbox{}\verb@      this container; dont need to check "ea" because that is a@\\
\mbox{}\verb@      string of length 2*/@\\
\mbox{}\verb@      if((*iter).find("a")<(*iter).size())@\\
\mbox{}\verb@      {@\\
\mbox{}\verb@        cout<<"String in length 1 container contains an ""a""";@\\
\mbox{}\verb@        cout<<endl;@\\
\mbox{}\verb@        return false;@\\
\mbox{}\verb@      }@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  if(sorted[3].size() != 18252)  @\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    cout<<"Length 2 failed"<<endl;@\\
\mbox{}\verb@    return false;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  else@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    //check every string to make sure it is of length 2@\\
\mbox{}\verb@    for(iter = sorted[3].begin();iter != sorted[3].end();iter++)@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      if((*iter).size() != 2)@\\
\mbox{}\verb@      {@\\
\mbox{}\verb@        cout<<"String in length 2 container contains a string of ";@\\
\mbox{}\verb@        cout<<"not length 2"<<endl;@\\
\mbox{}\verb@        return false;@\\
\mbox{}\verb@      }@\\
\mbox{}\verb@      /*also need to check to make sure that there are no 'a's in@\\
\mbox{}\verb@      this contianer; dont need to check "ea" because that is@\\
\mbox{}\verb@      contains an 'a' and would be caught by the check for 'a's*/@\\
\mbox{}\verb@      if((*iter).find("a")<(*iter).size())@\\
\mbox{}\verb@      {@\\
\mbox{}\verb@        cout<<"String in length 2 container contains an ""a""";@\\
\mbox{}\verb@        cout<<endl;@\\
\mbox{}\verb@        return false;@\\
\mbox{}\verb@      }@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  if(sorted[4].size() != 0)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    /*there are strings in the container for begins with "a" and@\\
\mbox{}\verb@    there shouldn't be*/@\\
\mbox{}\verb@      cout<<"Begins letter """<<(char)(97);@\\
\mbox{}\verb@      cout<<""" failed"<<endl;@\\
\mbox{}\verb@      return false;@\\
\mbox{}\verb@  }    @\\
\mbox{}\verb@  for(int i = 5;i<30;i++)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    if(sorted[i].size() != 676)@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      cout<<"Begins letter """<<(char)(i+93)<<""" failed"<<endl;@\\
\mbox{}\verb@      return false;@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@    else@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      /*check each string to make sure it starts with the correct@\\
\mbox{}\verb@      letter*/@\\
\mbox{}\verb@      for(iter = sorted[i].begin();iter != sorted[i].end();iter++)@\\
\mbox{}\verb@      {@\\
\mbox{}\verb@        if((*iter)[0] != (char)(i+93))@\\
\mbox{}\verb@        {@\\
\mbox{}\verb@          cout<<"String in begins with "<<(char)(i+93);@\\
\mbox{}\verb@          cout<<" container ";@\\
\mbox{}\verb@          cout<<"contains a string beginning with ";@\\
\mbox{}\verb@          cout<<(*iter)[0]<<endl;@\\
\mbox{}\verb@          return false;@\\
\mbox{}\verb@        }@\\
\mbox{}\verb@        /*also need to check to make sure that there are no 'a's in@\\
\mbox{}\verb@        this container; dont need to check "ea" because that is@\\
\mbox{}\verb@        contains an 'a' and would be caught by the check for 'a's*/@\\
\mbox{}\verb@        if((*iter).find("a")<(*iter).size())@\\
\mbox{}\verb@        {@\\
\mbox{}\verb@          cout<<"Begins letter """<<(char)(i+93);@\\
\mbox{}\verb@          cout<<""" contains the letter 'a'"<<endl;@\\
\mbox{}\verb@          return false;@\\
\mbox{}\verb@        }@\\
\mbox{}\verb@        /*also need to check that the string length of the string@\\
\mbox{}\verb@        is greater than 2*/@\\
\mbox{}\verb@        if((*iter).size() < 3)@\\
\mbox{}\verb@        {@\\
\mbox{}\verb@          cout<<"Begins letter """<<(char)(i+93);@\\
\mbox{}\verb@          cout<<""" contains a string of length ";@\\
\mbox{}\verb@          cout<<(*iter).size()<<endl;@\\
\mbox{}\verb@          return false;@\\
\mbox{}\verb@        }@\\
\mbox{}\verb@      }@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  if(sorted[30].size() != 676)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    cout<<"Default case failed"<<endl;@\\
\mbox{}\verb@    return false;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  else@\\
\mbox{}\verb@  {/*check to make sure that every string here begins with a "{"@\\
\mbox{}\verb@   and that it does not contain an 'a' and is of length@\\
\mbox{}\verb@   greater than 2*/@\\
\mbox{}\verb@    for(iter = sorted[30].begin();iter != sorted[30].end();iter++)@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      if((*iter)[0] != (char)(123))@\\
\mbox{}\verb@      {@\\
\mbox{}\verb@        cout<<"String in begins with "<<(char)(123)<<" container ";@\\
\mbox{}\verb@        cout<<"contains a string beginning with ";@\\
\mbox{}\verb@        cout<<(*iter)[0]<<endl;@\\
\mbox{}\verb@        return false;@\\
\mbox{}\verb@      }@\\
\mbox{}\verb@      /*also need to check to make sure that there are no 'a's in@\\
\mbox{}\verb@      tihs container; dont need to check "ea" because that is@\\
\mbox{}\verb@      contains an 'a' and would be caught by the check for 'a's*/@\\
\mbox{}\verb@      if((*iter).find("a")<(*iter).size())@\\
\mbox{}\verb@      {@\\
\mbox{}\verb@        cout<<"Begins letter """<<(char)(123);@\\
\mbox{}\verb@        cout<<""" contains the letter 'a'"<<endl;@\\
\mbox{}\verb@        return false;@\\
\mbox{}\verb@      }@\\
\mbox{}\verb@      /*also need to check that the string length of the string is@\\
\mbox{}\verb@      greater than 2*/@\\
\mbox{}\verb@      if((*iter).size() < 3)@\\
\mbox{}\verb@      {@\\
\mbox{}\verb@        cout<<"Begins letter """<<(char)(123);@\\
\mbox{}\verb@        cout<<""" contains a ";@\\
\mbox{}\verb@        cout<<"string of length "<<(*iter).size()<<endl;@\\
\mbox{}\verb@        return false;@\\
\mbox{}\verb@      }@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  return true;@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@
\end{list}
\vspace{-2ex}
\end{flushleft}
\section{Insert Iterator Tests}
\label{sec-code-test-insert-iter}
\begin{flushleft} \small \label{part122}
\verb@"test_inserters.cpp"@ {\footnotesize \hypertarget{253}{253} }$\equiv$
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@//test_inserters.cpp version 1.1@\\
\mbox{}\verb@#include <iostream>@\\
\mbox{}\verb@#include <fstream>@\\
\mbox{}\verb@#include <string>@\\
\mbox{}\verb@#include <ctype.h>@\\
\mbox{}\verb@#include <deque>@\\
\mbox{}\verb@#include <list>@\\
\mbox{}\verb@#include "router.hpp"@\\
\mbox{}\verb@#include "test_classes.hpp"@\\
\mbox{}\verb@#include "validate.hpp"@\\
\mbox{}\verb@using std::cout;@\\
\mbox{}\verb@using std::endl;@\\
\mbox{}\verb@using std::vector;@\\
\mbox{}\verb@using std::list;@\\
\mbox{}\verb@using std::deque;@\\
\mbox{}\verb@using std::back_inserter;@\\
\mbox{}\verb@using std::front_inserter;@\\
\mbox{}\verb@using std::istream_iterator;@\\
\mbox{}\verb@using std::back_insert_iterator;@\\
\mbox{}\verb@using std::front_insert_iterator;@\\
\mbox{}\verb@using std::string;@\\
\mbox{}\verb@using std::cin;@\\
\mbox{}\verb@@\\
\mbox{}\verb@using gdfa::router;@\\
\mbox{}\verb@using gdfa::destination;@\\
\mbox{}\verb@@\\
\mbox{}\verb@template<typename InputIterator>@\\
\mbox{}\verb@bool testbackdeque(vector<string> results[27],InputIterator begin,@\\
\mbox{}\verb@                   InputIterator end);@\\
\mbox{}\verb@template<typename InputIterator>@\\
\mbox{}\verb@bool testbacklist(vector<string> results[27],InputIterator begin,@\\
\mbox{}\verb@                  InputIterator end);@\\
\mbox{}\verb@template<typename InputIterator>@\\
\mbox{}\verb@bool testfrontdeque(vector<string> results[27],InputIterator begin,@\\
\mbox{}\verb@                    InputIterator end);@\\
\mbox{}\verb@template<typename InputIterator>@\\
\mbox{}\verb@bool testfrontlist(vector<string> results[27],InputIterator begin,@\\
\mbox{}\verb@                   InputIterator end);@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@int main(int argc,char *argv[])@\\
\mbox{}\verb@{@\\
\mbox{}\verb@@\\
\mbox{}\verb@  cout << "\n\n\ntestinserters.cpp\n\n"@\\
\mbox{}\verb@    << "Test of Reading from Standard Library Containers\n"@\\
\mbox{}\verb@    << "using front or back inserters (where applicable).\n"@\\
\mbox{}\verb@    << "*************************************************"@\\
\mbox{}\verb@    << "\n\n"@\\
\mbox{}\verb@    << "Results:\n\n";@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@  router<string> r;@\\
\mbox{}\verb@  vector<string> sorted[27];//one for each letter, one for default@\\
\mbox{}\verb@  word_sorter<back_insert_iterator<vector<string> > > *dummy[26];@\\
\mbox{}\verb@  for(int i = 0; i<26;i++)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    dummy[i] =@\\
\mbox{}\verb@     new word_sorter<back_insert_iterator<vector<string> > >@\\
\mbox{}\verb@     (back_inserter(sorted[i]),(char)(i + 97));@\\
\mbox{}\verb@    r.add_destination(*dummy[i]);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  my_default<back_insert_iterator<vector<string> > >@\\
\mbox{}\verb@   dflt(back_inserter(sorted[26]));@\\
\mbox{}\verb@  r.set_default(dflt);@\\
\mbox{}\verb@  typedef istream_iterator<string> in_string;@\\
\mbox{}\verb@  vector<string> storage_for_later;@\\
\mbox{}\verb@  in_string input(cin);@\\
\mbox{}\verb@  while(input != in_string())@\\
\mbox{}\verb@    storage_for_later.push_back(*input++);@\\
\mbox{}\verb@@\\
\mbox{}\verb@  //distribute@\\
\mbox{}\verb@  r.distribute(storage_for_later.begin(),storage_for_later.end());@\\
\mbox{}\verb@  cout<<"Results for filtering into vector using a back insert ";@\\
\mbox{}\verb@  cout<<"iterator.  Will be used for testing other insert ";@\\
\mbox{}\verb@  cout<<"iterators"<<endl;@\\
\mbox{}\verb@  cout<<"Number of words beginning with each letter, case ";@\\
\mbox{}\verb@  cout<<"insensitive:"<<endl;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  for(int i = 0;i<26;i++)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    cout<<(char)(i + 97)<<": "<<sorted[i].size()<<endl;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  cout<<"Default: "<<sorted[26].size()<<endl<<endl;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  cout<<"Testing back insert iterator deque"<<endl;@\\
\mbox{}\verb@  if(testbackdeque(sorted,storage_for_later.begin(),@\\
\mbox{}\verb@     storage_for_later.end()))@\\
\mbox{}\verb@    cout<<"Passed test for back insert iterator deque"<<endl;@\\
\mbox{}\verb@  else@\\
\mbox{}\verb@    cout<<"Failed test for back insert iterator deque"<<endl;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  cout<<"Testing back insert iterator list"<<endl;@\\
\mbox{}\verb@  if(testbacklist(sorted,storage_for_later.begin(),@\\
\mbox{}\verb@     storage_for_later.end()))@\\
\mbox{}\verb@    cout<<"Passed test for back insert iterator list"<<endl;@\\
\mbox{}\verb@  else@\\
\mbox{}\verb@    cout<<"Failed test for back insert iterator list"<<endl;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  cout<<"Testing front insert iterator deque"<<endl;@\\
\mbox{}\verb@  if(testfrontdeque(sorted,storage_for_later.begin(),@\\
\mbox{}\verb@     storage_for_later.end()))@\\
\mbox{}\verb@    cout<<"Passed test for front insert iterator deque"<<endl;@\\
\mbox{}\verb@  else@\\
\mbox{}\verb@    cout<<"Failed test for front insert iterator deque"<<endl;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  cout<<"Testing front insert iterator list"<<endl;@\\
\mbox{}\verb@  if(testfrontlist(sorted,storage_for_later.begin(),@\\
\mbox{}\verb@     storage_for_later.end()))@\\
\mbox{}\verb@    cout<<"Passed test for front insert iterator list"<<endl;@\\
\mbox{}\verb@  else@\\
\mbox{}\verb@    cout<<"Failed test for front insert iterator list"<<endl;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  cout<<"\n*************     END OF RESULTS     *************";@\\
\mbox{}\verb@  cout<<"\n\n";@\\
\mbox{}\verb@@\\
\mbox{}\verb@  return 0;@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@template<typename InputIterator>@\\
\mbox{}\verb@bool testbackdeque(vector<string> results[27],InputIterator begin,@\\
\mbox{}\verb@                   InputIterator end)@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  router<string> r;@\\
\mbox{}\verb@  deque<string> sorted[27];//one for each letter, one for default@\\
\mbox{}\verb@  word_sorter<back_insert_iterator<deque<string> > > *dummy[26];@\\
\mbox{}\verb@  for(int i = 0; i<26;i++)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    dummy[i] =@\\
\mbox{}\verb@     new word_sorter<back_insert_iterator<deque<string> > >@\\
\mbox{}\verb@     (back_inserter(sorted[i]),(char)(i + 97));@\\
\mbox{}\verb@    r.add_destination(*dummy[i]);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  my_default<back_insert_iterator<deque<string> > >@\\
\mbox{}\verb@   dflt(back_inserter(sorted[26]));@\\
\mbox{}\verb@  r.set_default(dflt);@\\
\mbox{}\verb@  r.distribute(begin,end);@\\
\mbox{}\verb@  return validate(results,sorted,27);@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@\\
\mbox{}\verb@template<typename InputIterator>@\\
\mbox{}\verb@bool testfrontdeque(vector<string> results[27],InputIterator begin,@\\
\mbox{}\verb@                    InputIterator end)@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  router<string> r;@\\
\mbox{}\verb@  deque<string> sorted[27];//one for each letter, one for default@\\
\mbox{}\verb@  word_sorter<front_insert_iterator<deque<string> > > *dummy[26];@\\
\mbox{}\verb@  for(int i = 0; i<26;i++)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    dummy[i] =@\\
\mbox{}\verb@     new word_sorter<front_insert_iterator<deque<string> > >@\\
\mbox{}\verb@     (front_inserter(sorted[i]),(char)(i + 97));@\\
\mbox{}\verb@    r.add_destination(*dummy[i]);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  my_default<front_insert_iterator<deque<string> > >@\\
\mbox{}\verb@   dflt(front_inserter(sorted[26]));@\\
\mbox{}\verb@  r.set_default(dflt);@\\
\mbox{}\verb@  r.distribute(begin,end);@\\
\mbox{}\verb@  return validate(results,sorted,27,true);@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@\\
\mbox{}\verb@template<typename InputIterator>@\\
\mbox{}\verb@bool testbacklist(vector<string> results[27],InputIterator begin,@\\
\mbox{}\verb@                  InputIterator end)@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  router<string> r;@\\
\mbox{}\verb@  list<string> sorted[27];//one for each letter, one for default@\\
\mbox{}\verb@  word_sorter<back_insert_iterator<list<string> > > *dummy[26];@\\
\mbox{}\verb@  for(int i = 0; i<26;i++)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    dummy[i] =@\\
\mbox{}\verb@     new word_sorter<back_insert_iterator<list<string> > >@\\
\mbox{}\verb@     (back_inserter(sorted[i]),(char)(i + 97));@\\
\mbox{}\verb@    r.add_destination(*dummy[i]);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  my_default<back_insert_iterator<list<string> > >@\\
\mbox{}\verb@   dflt(back_inserter(sorted[26]));@\\
\mbox{}\verb@  r.set_default(dflt);@\\
\mbox{}\verb@  r.distribute(begin,end);@\\
\mbox{}\verb@  return validate(results,sorted,27);@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@\\
\mbox{}\verb@template<typename InputIterator>@\\
\mbox{}\verb@bool testfrontlist(vector<string> results[27],InputIterator begin,@\\
\mbox{}\verb@                   InputIterator end)@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  router<string> r;@\\
\mbox{}\verb@  list<string> sorted[27];//one for each letter, one for default@\\
\mbox{}\verb@  word_sorter<front_insert_iterator<list<string> > > *dummy[26];@\\
\mbox{}\verb@  for(int i = 0; i<26;i++)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    dummy[i] =@\\
\mbox{}\verb@     new word_sorter<front_insert_iterator<list<string> > >@\\
\mbox{}\verb@     (front_inserter(sorted[i]),(char)(i + 97));@\\
\mbox{}\verb@    r.add_destination(*dummy[i]);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  my_default<front_insert_iterator<list<string> > >@\\
\mbox{}\verb@   dflt(front_inserter(sorted[26]));@\\
\mbox{}\verb@  r.set_default(dflt);@\\
\mbox{}\verb@  r.distribute(begin,end);@\\
\mbox{}\verb@  return validate(results,sorted,27,true);@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@
\end{list}
\vspace{-2ex}
\end{flushleft}
\section{Standard Library Containers Read Tests}
\label{sec-code-test-read-cont}
\begin{flushleft} \small \label{part123}
\verb@"testreadcont.cpp"@ {\footnotesize \hypertarget{257}{257} }$\equiv$
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@//testreadcont.cpp version 1.1@\\
\mbox{}\verb@#include <iostream>@\\
\mbox{}\verb@#include <fstream>@\\
\mbox{}\verb@#include <string>@\\
\mbox{}\verb@#include <ctype.h>@\\
\mbox{}\verb@#include <set>@\\
\mbox{}\verb@#include <deque>@\\
\mbox{}\verb@#include <list>@\\
\mbox{}\verb@#include <map>@\\
\mbox{}\verb@#include "router.hpp"@\\
\mbox{}\verb@#include "test_classes.hpp"@\\
\mbox{}\verb@#include "validate.hpp"@\\
\mbox{}\verb@using std::cout;@\\
\mbox{}\verb@using std::endl;@\\
\mbox{}\verb@using std::vector;@\\
\mbox{}\verb@using std::deque;@\\
\mbox{}\verb@using std::multiset;@\\
\mbox{}\verb@using std::list;@\\
\mbox{}\verb@using std::back_inserter;@\\
\mbox{}\verb@using std::istream_iterator;@\\
\mbox{}\verb@using std::back_insert_iterator;@\\
\mbox{}\verb@using std::string;@\\
\mbox{}\verb@using std::cin;@\\
\mbox{}\verb@using std::map;@\\
\mbox{}\verb@using std::pair;@\\
\mbox{}\verb@@\\
\mbox{}\verb@using gdfa::router;@\\
\mbox{}\verb@using gdfa::destination;@\\
\mbox{}\verb@@\\
\mbox{}\verb@template<typename InputIterator>@\\
\mbox{}\verb@bool testdeque(vector<string> results[27], InputIterator begin,@\\
\mbox{}\verb@               InputIterator end);@\\
\mbox{}\verb@template<typename InputIterator>@\\
\mbox{}\verb@bool testmultiset(vector<string> results[27], InputIterator begin,@\\
\mbox{}\verb@                  InputIterator end);@\\
\mbox{}\verb@template<typename InputIterator>@\\
\mbox{}\verb@bool testlist(vector<string> results[27], InputIterator begin,@\\
\mbox{}\verb@              InputIterator end);@\\
\mbox{}\verb@template<typename InputIterator>@\\
\mbox{}\verb@bool testmap(vector<string> results[27], InputIterator begin,@\\
\mbox{}\verb@             InputIterator end);@\\
\mbox{}\verb@template<typename conttype1,typename conttype2>@\\
\mbox{}\verb@bool validatemap(conttype1 key[],conttype2 res[],int size);@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@int main(int argc,char *argv[])@\\
\mbox{}\verb@{@\\
\mbox{}\verb@@\\
\mbox{}\verb@  cout << "\n\n\nTest:   testreadcont.cpp\n\n"@\\
\mbox{}\verb@     << "Test Reading from Standard Library Containers\n"@\\
\mbox{}\verb@     << "*********************************************\n\n"@\\
\mbox{}\verb@     << "Results:\n\n";@\\
\mbox{}\verb@@\\
\mbox{}\verb@  //first thing to do is read all the input into a container@\\
\mbox{}\verb@  typedef istream_iterator<string> in_string;@\\
\mbox{}\verb@  string input;@\\
\mbox{}\verb@  vector<string> storage;@\\
\mbox{}\verb@  while(cin>>input)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    storage.push_back(input);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  router<string> r;@\\
\mbox{}\verb@  vector<string> sorted[27];//one for each letter, one for default@\\
\mbox{}\verb@  word_sorter<back_insert_iterator<vector<string> > > *dummy[26];@\\
\mbox{}\verb@  for(int i = 0; i<26;i++)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    dummy[i] =@\\
\mbox{}\verb@     new word_sorter<back_insert_iterator<vector<string> > >@\\
\mbox{}\verb@     (back_inserter(sorted[i]),(char)(i + 97));@\\
\mbox{}\verb@    r.add_destination(*dummy[i]);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  my_default<back_insert_iterator<vector<string> > >@\\
\mbox{}\verb@   dflt(back_inserter(sorted[26]));@\\
\mbox{}\verb@  r.set_default(dflt);@\\
\mbox{}\verb@  r.distribute(storage.begin(),storage.end());@\\
\mbox{}\verb@  cout<<"Results for reading from a vector, used for comparison ";@\\
\mbox{}\verb@  cout<<"testing"<<endl;@\\
\mbox{}\verb@  cout<<"Number of words beginning with each letter, case ";@\\
\mbox{}\verb@  cout<<"insensitive"<<endl;@\\
\mbox{}\verb@  for(int i = 0;i<26;i++)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    cout<<(char)(i + 97)<<": "<<sorted[i].size()<<endl;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  cout<<"default: "<<sorted[26].size()<<endl<<endl;@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  cout<<"Testing reading from a deque"<<endl;@\\
\mbox{}\verb@  if(testdeque(sorted,storage.begin(),storage.end()))@\\
\mbox{}\verb@    cout<<"Passed test for reading from a deque"<<endl;@\\
\mbox{}\verb@  else@\\
\mbox{}\verb@    cout<<"Failed test for reading from a deque"<<endl;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  cout<<"Testing reading from a list"<<endl;@\\
\mbox{}\verb@  if(testlist(sorted,storage.begin(),storage.end()))@\\
\mbox{}\verb@    cout<<"Passed test for reading from a list"<<endl;@\\
\mbox{}\verb@  else@\\
\mbox{}\verb@    cout<<"Failed test for reading from a list"<<endl;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  cout<<"Testing reading from a multiset"<<endl;@\\
\mbox{}\verb@  if(testmultiset(sorted,storage.begin(),storage.end()))@\\
\mbox{}\verb@    cout<<"Passed test for reading from a multiset"<<endl;@\\
\mbox{}\verb@  else@\\
\mbox{}\verb@    cout<<"Failed test for reading from a multiset"<<endl;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  cout<<"Testing reading from a map"<<endl;@\\
\mbox{}\verb@  if(testmap(sorted,storage.begin(),storage.end()))@\\
\mbox{}\verb@    cout<<"Passed test for reading from a map"<<endl;@\\
\mbox{}\verb@  else@\\
\mbox{}\verb@    cout<<"Failed test for reading from a map"<<endl;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  cout<<"\n*************     END OF RESULTS     *************\n\n";@\\
\mbox{}\verb@@\\
\mbox{}\verb@  return 0;@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@\\
\mbox{}\verb@template<typename InputIterator>@\\
\mbox{}\verb@bool testdeque(vector<string> results[27], InputIterator begin,@\\
\mbox{}\verb@               InputIterator end)@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  deque<string> storage(begin,end);@\\
\mbox{}\verb@  router<string> r;@\\
\mbox{}\verb@  vector<string> sorted[27];//one for each letter, one for default@\\
\mbox{}\verb@  word_sorter<back_insert_iterator<vector<string> > > *dummy[26];@\\
\mbox{}\verb@  for(int i = 0; i<26;i++)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    dummy[i] =@\\
\mbox{}\verb@     new word_sorter<back_insert_iterator<vector<string> > >@\\
\mbox{}\verb@     (back_inserter(sorted[i]),(char)(i + 97));@\\
\mbox{}\verb@    r.add_destination(*dummy[i]);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  my_default<back_insert_iterator<vector<string> > >@\\
\mbox{}\verb@   dflt(back_inserter(sorted[26]));@\\
\mbox{}\verb@  r.set_default(dflt);@\\
\mbox{}\verb@  r.distribute(storage.begin(),storage.end());@\\
\mbox{}\verb@  validate(results,sorted,27);@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@\\
\mbox{}\verb@template<typename InputIterator>@\\
\mbox{}\verb@bool testmultiset(vector<string> results[27], InputIterator begin,@\\
\mbox{}\verb@                  InputIterator end)@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  multiset<string> storage;@\\
\mbox{}\verb@  while(begin != end)@\\
\mbox{}\verb@    storage.insert(*begin++);@\\
\mbox{}\verb@@\\
\mbox{}\verb@  router<string> r;@\\
\mbox{}\verb@  vector<string> sorted[27];//one for each letter, one for default@\\
\mbox{}\verb@  word_sorter<back_insert_iterator<vector<string> > > *dummy[26];@\\
\mbox{}\verb@  for(int i = 0; i<26;i++)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    dummy[i] =@\\
\mbox{}\verb@     new word_sorter<back_insert_iterator<vector<string> > >@\\
\mbox{}\verb@     (back_inserter(sorted[i]),(char)(i + 97));@\\
\mbox{}\verb@    r.add_destination(*dummy[i]);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  my_default<back_insert_iterator<vector<string> > >@\\
\mbox{}\verb@    dflt(back_inserter(sorted[26]));@\\
\mbox{}\verb@  r.set_default(dflt);@\\
\mbox{}\verb@  r.distribute(storage.begin(),storage.end());@\\
\mbox{}\verb@  /*because a set is not sequential, the sequential validate test@\\
\mbox{}\verb@  is not applicable and a validation test based on the size of@\\
\mbox{}\verb@  the sorted vectors is used*/@\\
\mbox{}\verb@  validatesize(results,sorted,27);@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@\\
\mbox{}\verb@template<typename InputIterator>@\\
\mbox{}\verb@bool testlist(vector<string> results[27], InputIterator begin,@\\
\mbox{}\verb@              InputIterator end)@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  list<string> storage(begin,end);@\\
\mbox{}\verb@  router<string> r;@\\
\mbox{}\verb@  vector<string> sorted[27];//one for each letter, one for default@\\
\mbox{}\verb@  word_sorter<back_insert_iterator<vector<string> > > *dummy[26];@\\
\mbox{}\verb@  for(int i = 0; i<26;i++)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    dummy[i] =@\\
\mbox{}\verb@     new word_sorter<back_insert_iterator<vector<string> > >@\\
\mbox{}\verb@     (back_inserter(sorted[i]),(char)(i + 97));@\\
\mbox{}\verb@    r.add_destination(*dummy[i]);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  my_default<back_insert_iterator<vector<string> > >@\\
\mbox{}\verb@   dflt(back_inserter(sorted[26]));@\\
\mbox{}\verb@  r.set_default(dflt);@\\
\mbox{}\verb@  r.distribute(storage.begin(),storage.end());@\\
\mbox{}\verb@  validate(results,sorted,27);@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@\\
\mbox{}\verb@template<typename InputIterator>@\\
\mbox{}\verb@bool testmap(vector<string> results[27], InputIterator begin,@\\
\mbox{}\verb@             InputIterator end)@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  string input;@\\
\mbox{}\verb@  map<string,int> storage;@\\
\mbox{}\verb@  while(begin != end)@\\
\mbox{}\verb@    storage[*begin++]++;@\\
\mbox{}\verb@  router<pair<string,int> > r;@\\
\mbox{}\verb@  //one for each letter, one for default@\\
\mbox{}\verb@  vector<pair<string,int> > sorted[27];@\\
\mbox{}\verb@  word_sortermap<back_insert_iterator<vector<pair<string,int> > > >@\\
\mbox{}\verb@   *dummy[26];@\\
\mbox{}\verb@  for(int i = 0; i<26;i++)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    dummy[i] =@\\
\mbox{}\verb@     new word_sortermap<back_insert_iterator<vector<@\\
\mbox{}\verb@      pair<string,int> > > >(back_inserter(sorted[i]),@\\
\mbox{}\verb@      (char)(i + 97));@\\
\mbox{}\verb@    r.add_destination(*dummy[i]);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  my_defaultmap<back_insert_iterator<vector<pair<string,int> > > >@\\
\mbox{}\verb@   dflt(back_inserter(sorted[26]));@\\
\mbox{}\verb@  r.set_default(dflt);@\\
\mbox{}\verb@  r.distribute(storage.begin(),storage.end());@\\
\mbox{}\verb@  return validatemap(results,sorted,27);@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@\\
\mbox{}\verb@/*validatemap() works by getting a sum of the number of words @\\
\mbox{}\verb@beginning with each letter (from res) and comparing it to the @\\
\mbox{}\verb@number of words beginning with each letter in the key.  key is @\\
\mbox{}\verb@generated from the baseline test*/@\\
\mbox{}\verb@template<typename conttype1,typename conttype2>@\\
\mbox{}\verb@bool validatemap(conttype1 key[],conttype2 res[],int size)@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  typedef typename conttype1::iterator key_iter;@\\
\mbox{}\verb@  key_iter ikey;@\\
\mbox{}\verb@  typedef typename conttype2::iterator res_iter;@\\
\mbox{}\verb@  res_iter ires;@\\
\mbox{}\verb@  for(int i = 0;i < size;i++)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    int total = 0;@\\
\mbox{}\verb@    for(vector<pair<string,int> >::iterator iter = res[i].begin();@\\
\mbox{}\verb@        iter!=res[i].end();iter++)@\\
\mbox{}\verb@      total += iter->second;@\\
\mbox{}\verb@    if(key[i].size() != total)@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      cout<<"match failed for container: "<<i<<endl;@\\
\mbox{}\verb@      return false;@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  return true;@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@
\end{list}
\vspace{-2ex}
\end{flushleft}
\section{Array Read Tests}
\label{sec-code-test-array}
\begin{flushleft} \small \label{part124}
\verb@"testarray.cpp"@ {\footnotesize \hypertarget{262}{262} }$\equiv$
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@//testarrayinput.cpp version 1.1@\\
\mbox{}\verb@#include <iostream>@\\
\mbox{}\verb@#include <fstream>@\\
\mbox{}\verb@#include <string>@\\
\mbox{}\verb@#include <ctype.h>@\\
\mbox{}\verb@#include "router.hpp"@\\
\mbox{}\verb@#include "test_classes.hpp"@\\
\mbox{}\verb@#include "validate.hpp"@\\
\mbox{}\verb@using std::cout;@\\
\mbox{}\verb@using std::endl;@\\
\mbox{}\verb@using std::vector;@\\
\mbox{}\verb@using std::back_inserter;@\\
\mbox{}\verb@using std::istream_iterator;@\\
\mbox{}\verb@using std::back_insert_iterator;@\\
\mbox{}\verb@using std::string;@\\
\mbox{}\verb@using std::cin;@\\
\mbox{}\verb@@\\
\mbox{}\verb@using gdfa::router;@\\
\mbox{}\verb@using gdfa::destination;@\\
\mbox{}\verb@@\\
\mbox{}\verb@bool filterarray(vector<string> results[],string storage[],@\\
\mbox{}\verb@                 int size);@\\
\mbox{}\verb@@\\
\mbox{}\verb@int main(int argc,char *argv[])@\\
\mbox{}\verb@{@\\
\mbox{}\verb@@\\
\mbox{}\verb@  cout << "\n\n\nTest:  testarray.cpp"@\\
\mbox{}\verb@    << "\n\nTest Using an Array as input.\n"@\\
\mbox{}\verb@    << "***********************************\n\n"@\\
\mbox{}\verb@    << "Results:\n\n";@\\
\mbox{}\verb@@\\
\mbox{}\verb@  router<string> r;@\\
\mbox{}\verb@  vector<string> sorted[27];//one for each letter, one for default@\\
\mbox{}\verb@  word_sorter<back_insert_iterator<vector<string> > > *dummy[26];@\\
\mbox{}\verb@  for(int i = 0; i<26;i++)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    dummy[i] =@\\
\mbox{}\verb@     new word_sorter<back_insert_iterator<vector<string> > >@\\
\mbox{}\verb@     (back_inserter(sorted[i]),(char)(i + 97));@\\
\mbox{}\verb@    r.add_destination(*dummy[i]);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  my_default<back_insert_iterator<vector<string> > >@\\
\mbox{}\verb@   dflt(back_inserter(sorted[26]));@\\
\mbox{}\verb@  r.set_default(dflt);@\\
\mbox{}\verb@@\\
\mbox{}\verb@  typedef istream_iterator<string> in_string;@\\
\mbox{}\verb@  vector<string> storage;@\\
\mbox{}\verb@  in_string input(cin);@\\
\mbox{}\verb@@\\
\mbox{}\verb@  while(input != in_string())@\\
\mbox{}\verb@    storage.push_back(*input++);@\\
\mbox{}\verb@@\\
\mbox{}\verb@  string *strarray = new string[storage.size()];@\\
\mbox{}\verb@  for(int i=0;i<storage.size();i++)@\\
\mbox{}\verb@    strarray[i] = storage[i];@\\
\mbox{}\verb@@\\
\mbox{}\verb@  //filtervector and print results@\\
\mbox{}\verb@  r.distribute(storage.begin(),storage.end());@\\
\mbox{}\verb@  for(int i = 0;i<26;i++)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    cout<<(char)(i + 97)<<": "<<sorted[i].size()<<endl;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  cout<<"default: "<<sorted[26].size()<<endl<<endl;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  //step 3, 4@\\
\mbox{}\verb@  //filter array and validate@\\
\mbox{}\verb@  cout<<"Testing using an array as input"<<endl;@\\
\mbox{}\verb@  if(filterarray(sorted,strarray,storage.size()))@\\
\mbox{}\verb@    cout<<"Passed array input test"<<endl;@\\
\mbox{}\verb@  else@\\
\mbox{}\verb@    cout<<"Failed array input test"<<endl;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  cout<<"\n*************     END OF RESULTS     *************\n\n";@\\
\mbox{}\verb@@\\
\mbox{}\verb@  return 0;@\\
\mbox{}\verb@}@\\
\mbox{}\verb@bool filterarray(vector<string> results[],string storage[],@\\
\mbox{}\verb@                 int size)@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  router<string> r;@\\
\mbox{}\verb@  vector<string> sorted[27];//one for each letter, one for default@\\
\mbox{}\verb@  word_sorter<back_insert_iterator<vector<string> > > *dummy[26];@\\
\mbox{}\verb@  for(int i = 0; i<26;i++)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    dummy[i] =@\\
\mbox{}\verb@     new word_sorter<back_insert_iterator<vector<string> > >@\\
\mbox{}\verb@     (back_inserter(sorted[i]),(char)(i + 97));@\\
\mbox{}\verb@    r.add_destination(*dummy[i]);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  my_default<back_insert_iterator<vector<string> > >@\\
\mbox{}\verb@   dflt(back_inserter(sorted[26]));@\\
\mbox{}\verb@  r.set_default(dflt);@\\
\mbox{}\verb@  r.distribute(&storage[0],&storage[size]);@\\
\mbox{}\verb@  return validate(results,sorted,27);@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@
\end{list}
\vspace{-2ex}
\end{flushleft}
\section{Tests Reading from and Writing to Files}
\label{sec-code-test-file-io}
\begin{flushleft} \small \label{part125}
\verb@"testrwfiles.cpp"@ {\footnotesize \hypertarget{264}{264} }$\equiv$
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@//testrwfiles.cpp version 1.0@\\
\mbox{}\verb@#include <iostream>@\\
\mbox{}\verb@#include <fstream>@\\
\mbox{}\verb@#include <string>@\\
\mbox{}\verb@#include <ctype.h>@\\
\mbox{}\verb@#include "router.hpp"@\\
\mbox{}\verb@using std::cout;@\\
\mbox{}\verb@using std::endl;@\\
\mbox{}\verb@using std::vector;@\\
\mbox{}\verb@using std::back_inserter;@\\
\mbox{}\verb@using std::istream_iterator;@\\
\mbox{}\verb@using std::ostream_iterator;@\\
\mbox{}\verb@using std::back_insert_iterator;@\\
\mbox{}\verb@using std::string;@\\
\mbox{}\verb@using std::cin;@\\
\mbox{}\verb@using std::ifstream;@\\
\mbox{}\verb@using std::ofstream;@\\
\mbox{}\verb@@\\
\mbox{}\verb@using gdfa::router;@\\
\mbox{}\verb@using gdfa::destination;@\\
\mbox{}\verb@@\\
\mbox{}\verb@template<typename output_iterator>@\\
\mbox{}\verb@class word_sorter : public destination<string>@\\
\mbox{}\verb@{@\\
\mbox{}\verb@   private:@\\
\mbox{}\verb@  output_iterator m_out;@\\
\mbox{}\verb@  char m_first_letter;@\\
\mbox{}\verb@  @\\
\mbox{}\verb@   public:@\\
\mbox{}\verb@  word_sorter(output_iterator out, char first_letter)@\\
\mbox{}\verb@         : m_out(out), m_first_letter(first_letter) {}@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  /*out distribute function checks the first letter to see if it is@\\
\mbox{}\verb@  the same as in the predicate*/@\\
\mbox{}\verb@  bool distribute(const string& element)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@     if (tolower((const int)element[0]) == m_first_letter)@\\
\mbox{}\verb@     {@\\
\mbox{}\verb@    *m_out++ = element;@\\
\mbox{}\verb@            *m_out++ = "\n";@\\
\mbox{}\verb@    return true;@\\
\mbox{}\verb@     }@\\
\mbox{}\verb@     @\\
\mbox{}\verb@     return false;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@};@\\
\mbox{}\verb@@\\
\mbox{}\verb@template<typename output_iterator>@\\
\mbox{}\verb@class my_default : public destination<string>@\\
\mbox{}\verb@{@\\
\mbox{}\verb@   private:@\\
\mbox{}\verb@  output_iterator m_out;@\\
\mbox{}\verb@   public:@\\
\mbox{}\verb@  my_default(output_iterator out)@\\
\mbox{}\verb@         : m_out(out) {}@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  bool distribute(const string& n)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@     *m_out++ = n;@\\
\mbox{}\verb@     return true;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@};@\\
\mbox{}\verb@@\\
\mbox{}\verb@int main(int argc,char *argv[])@\\
\mbox{}\verb@{  @\\
\mbox{}\verb@  cout << "\n\n\nTest:  testrwfiles.cpp\n\nTest of reading and";@\\
\mbox{}\verb@  cout<<"writing from and to files with ifstream and ofstream.\n"@\\
\mbox{}\verb@  <<"******************************"@\\
\mbox{}\verb@  <<"***************************\n\n";@\\
\mbox{}\verb@@\\
\mbox{}\verb@  //as a command line arguement it takes a file for input@\\
\mbox{}\verb@  if(argc != 2)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    cout<<"Usage ./app <inputfilename>"<<endl;@\\
\mbox{}\verb@    return 1;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  typedef ostream_iterator<string> out_string;@\\
\mbox{}\verb@  router<string> r;@\\
\mbox{}\verb@  ofstream output[27];//out for each letter and one for default@\\
\mbox{}\verb@  word_sorter<out_string> *dummy[26];@\\
\mbox{}\verb@  for(int i = 0; i<26;i++)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    string filename = "output_";@\\
\mbox{}\verb@    filename += (char)(i+97);@\\
\mbox{}\verb@    output[i].open(filename.c_str());@\\
\mbox{}\verb@    dummy[i] = new word_sorter<out_string>(out_string(output[i]),@\\
\mbox{}\verb@                                           (char)(i + 97));@\\
\mbox{}\verb@    r.add_destination(*dummy[i]);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  output[26].open("output_default");@\\
\mbox{}\verb@  my_default<out_string> dflt =@\\
\mbox{}\verb@   my_default<out_string>(out_string(output[26]));@\\
\mbox{}\verb@  r.set_default(dflt);@\\
\mbox{}\verb@  ifstream filein;@\\
\mbox{}\verb@  filein.open(argv[1]);@\\
\mbox{}\verb@  if(filein == NULL)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    cout<<argv[1]<<" invalid file"<<endl;@\\
\mbox{}\verb@    return 1;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  typedef istream_iterator<string> in_string;@\\
\mbox{}\verb@  r.distribute(in_string(filein),in_string());@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  cout<<"\n*************     END OF TEST     *************\n\n";@\\
\mbox{}\verb@@\\
\mbox{}\verb@  return 0;@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@
\end{list}
\vspace{-2ex}
\end{flushleft}
\begin{flushleft} \small \label{part126}
\verb@"validaterwfiles.cpp"@ {\footnotesize \hypertarget{266}{266} }$\equiv$
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@//validaterwfiles.cpp version 1.1@\\
\mbox{}\verb@@\\
\mbox{}\verb@#include <iterator>@\\
\mbox{}\verb@#include <iostream>@\\
\mbox{}\verb@#include <fstream>@\\
\mbox{}\verb@#include <string>@\\
\mbox{}\verb@#include <ctype.h>@\\
\mbox{}\verb@@\\
\mbox{}\verb@using std::cout;@\\
\mbox{}\verb@using std::endl;@\\
\mbox{}\verb@using std::istream_iterator;@\\
\mbox{}\verb@using std::ifstream;@\\
\mbox{}\verb@using std::string;@\\
\mbox{}\verb@@\\
\mbox{}\verb@typedef istream_iterator<string> string_in;@\\
\mbox{}\verb@@\\
\mbox{}\verb@int main(int argc, char *argv[])@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  cout << "\n\n\nTest:  validaterwfiles.cpp\n\n";@\\
\mbox{}\verb@  cout << "Validating the testrwfiles test. "@\\
\mbox{}\verb@  <<"\n*******************************"@\\
\mbox{}\verb@  <<"**************************\n\n"@\\
\mbox{}\verb@  << "Results:\n\n";@\\
\mbox{}\verb@@\\
\mbox{}\verb@  for(int i = 0;i<26;i++)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    string file = "output_";@\\
\mbox{}\verb@    file += (char)(i+97);@\\
\mbox{}\verb@    ifstream input(file.c_str());@\\
\mbox{}\verb@    if(input == NULL)@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      cout<<"Could not open file: "<<file<<endl;@\\
\mbox{}\verb@      return 0;@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@    string_in reader(input);@\\
\mbox{}\verb@    while(reader != string_in())@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      if(tolower((*reader)[0]) != (i+97))@\\
\mbox{}\verb@      {@\\
\mbox{}\verb@        cout<<"Test Failed"<<endl;@\\
\mbox{}\verb@        cout<<"In file: "<<file<<" string: "<<*reader;@\\
\mbox{}\verb@        cout<<" doesn't begin with a(n) """<<(char)(i+97);@\\
\mbox{}\verb@        cout<<"""."<<endl;@\\
\mbox{}\verb@        return 0;@\\
\mbox{}\verb@      }@\\
\mbox{}\verb@      reader++;@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@    input.close();@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  string file = "output_default";@\\
\mbox{}\verb@  ifstream input(file.c_str());@\\
\mbox{}\verb@  if(input == NULL)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    cout<<"Could not open file: "<<file<<endl;@\\
\mbox{}\verb@    return 0;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  string_in reader(input);@\\
\mbox{}\verb@  while(reader != string_in())@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    //we want to check vs lowercase chars@\\
\mbox{}\verb@    if(tolower((int)(*reader)[0]) > 96 &&@\\
\mbox{}\verb@       tolower((int)(*reader)[0]) < 123)@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      cout<<"Test Failed"<<endl;@\\
\mbox{}\verb@      cout<<"In file: "<<file<<" string: "<<*reader;@\\
\mbox{}\verb@      cout<<" begins with a(n) """<<(*reader)[0];@\\
\mbox{}\verb@      cout<<"""."<<endl;@\\
\mbox{}\verb@      return 0;@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@    reader++;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  input.close();@\\
\mbox{}\verb@  cout<<"Passed rwfiles test"<<endl;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  cout<<"\n*************     END OF RESULTS     *************\n\n";@\\
\mbox{}\verb@  return 0;@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@
\end{list}
\vspace{-2ex}
\end{flushleft}
\section{Tests with \code{std::istream\_iterator}s}
\subsection{Number Generation Utilities}
\subsubsection{\code{int} Generator}
\label{sec-code-test-gen-ints}
\begin{flushleft} \small \label{part127}
\verb@"genints.cpp"@ {\footnotesize \hypertarget{268a}{268a} }$\equiv$
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@#include <iostream>@\\
\mbox{}\verb@#include "random.h"@\\
\mbox{}\verb@#include <time.h>@\\
\mbox{}\verb@@\\
\mbox{}\verb@using namespace std;@\\
\mbox{}\verb@@\\
\mbox{}\verb@int main(int argc,char *argv[])@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  if(argc != 2)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    cout<<"Usage: ./genints <number_of_ints_to_generate>";@\\
\mbox{}\verb@    cout<<endl;@\\
\mbox{}\verb@    return -1;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  int num = atoi(argv[1]);@\\
\mbox{}\verb@  randgen.seed(time(NULL));@\\
\mbox{}\verb@  for(int i = 0;i<num;i++)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    cout<<randgen(1000000)<<endl;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  return 0;@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@
\end{list}
\vspace{-2ex}
\end{flushleft}
\subsubsection{\code{double} Generator}
\label{sec-code-test-gen-doubles}
\begin{flushleft} \small \label{part128}
\verb@"gendoubles.cpp"@ {\footnotesize \hypertarget{268b}{268b} }$\equiv$
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@#include <iostream>@\\
\mbox{}\verb@#include "random.h"@\\
\mbox{}\verb@#include <time.h>@\\
\mbox{}\verb@@\\
\mbox{}\verb@using namespace std;@\\
\mbox{}\verb@@\\
\mbox{}\verb@int main(int argc,char *argv[])@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  if(argc != 2)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    cout<<"Usage: ./gendouble <number_of_doubles_to_generate>";@\\
\mbox{}\verb@    cout<<endl;@\\
\mbox{}\verb@    return -1;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  int num = atoi(argv[1]);@\\
\mbox{}\verb@  randgen.seed(time(NULL));@\\
\mbox{}\verb@  for(int i = 0;i<num;i++)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    cout<<randgen()<<endl;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  return 0;@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@
\end{list}
\vspace{-2ex}
\end{flushleft}
\subsubsection{Random Number Utility}
The following utility is utilised by the random \code{int} generator 
(Appendix \ref{sec-code-test-gen-ints}) and the random \code{double} 
generator (Appendix \ref{sec-code-test-gen-doubles}).

\begin{flushleft} \small \label{part129}
\verb@"random.h"@ {\footnotesize \hypertarget{269}{269} }$\equiv$
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@/*@\\
\mbox{}\verb@ *@\\
\mbox{}\verb@ * Copyright (c) 1994@\\
\mbox{}\verb@ * Hewlett-Packard Company@\\
\mbox{}\verb@ *@\\
\mbox{}\verb@ * Permission to use, copy, modify, distribute and sell this @\\
\mbox{}\verb@ * software and its documentation for any purpose is hereby @\\
\mbox{}\verb@ * granted without fee, provided that the above copyright notice @\\
\mbox{}\verb@ * appear in all copies and that both that copyright notice and @\\
\mbox{}\verb@ * this permission notice appear in supporting documentation.  @\\
\mbox{}\verb@ * Hewlett-Packard Company makes no representations about the @\\
\mbox{}\verb@ * suitability of this software for any purpose.  It is provided @\\
\mbox{}\verb@ * "as is" without express or implied warranty.@\\
\mbox{}\verb@ *@\\
\mbox{}\verb@ */@\\
\mbox{}\verb@@\\
\mbox{}\verb@/*@\\
\mbox{}\verb@ * void randgen.seed(unsigned long j)  reseeds the generator with j@\\
\mbox{}\verb@ *    @\\
\mbox{}\verb@ * unsigned long ranggen(unsigned long limit)   @\\
\mbox{}\verb@ *     returns a pseudo-random number n, 0 <= n < limit,@\\
\mbox{}\verb@ *     uniformly distributed@\\
\mbox{}\verb@ *@\\
\mbox{}\verb@ * double randgen()@\\
\mbox{}\verb@ *     returns a pseudo-random number d, 0.0 <= n < 1.0,@\\
\mbox{}\verb@ *     uniformly distributed@\\
\mbox{}\verb@ */@\\
\mbox{}\verb@#ifndef _RANDOM_H@\\
\mbox{}\verb@#define _RANDOM_H@\\
\mbox{}\verb@@\\
\mbox{}\verb@#include <stddef.h>@\\
\mbox{}\verb@#include <climits>  // for ULONG_MAX@\\
\mbox{}\verb@@\\
\mbox{}\verb@#define __SEED 161803398@\\
\mbox{}\verb@@\\
\mbox{}\verb@class random_generator {@\\
\mbox{}\verb@protected:@\\
\mbox{}\verb@    unsigned long table[55];@\\
\mbox{}\verb@    size_t index1;@\\
\mbox{}\verb@    size_t index2;@\\
\mbox{}\verb@public:@\\
\mbox{}\verb@    unsigned long operator()(unsigned long limit) {@\\
\mbox{}\verb@                index1 = (index1 + 1) % 55;@\\
\mbox{}\verb@                index2 = (index2 + 1) % 55;@\\
\mbox{}\verb@                table[index1] -= table[index2];@\\
\mbox{}\verb@                return table[index1] % limit;@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@    inline double operator()() {@\\
\mbox{}\verb@        return (double)operator()(ULONG_MAX) / ULONG_MAX;@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@    void seed(unsigned long j);@\\
\mbox{}\verb@    random_generator(unsigned long j) { seed(j); }@\\
\mbox{}\verb@};@\\
\mbox{}\verb@@\\
\mbox{}\verb@void random_generator::seed(unsigned long j) {@\\
\mbox{}\verb@    unsigned long k = 1;@\\
\mbox{}\verb@    table[54] = j;@\\
\mbox{}\verb@    size_t i;@\\
\mbox{}\verb@    for (i = 0; i < 54; i++) {@\\
\mbox{}\verb@        size_t ii = (21 * (i + 1) % 55) - 1;@\\
\mbox{}\verb@        table[ii] = k;@\\
\mbox{}\verb@        k = j - k;@\\
\mbox{}\verb@        j = table[ii];@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@    for (int loop = 0; loop < 4; loop++) {@\\
\mbox{}\verb@        for (i = 0; i < 55; i++)@\\
\mbox{}\verb@            table[i] = table[i] - table[(1 + i + 30) % 55];@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@    index1 = 0;@\\
\mbox{}\verb@    index2 = 31;@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@\\
\mbox{}\verb@static random_generator randgen(__SEED);@\\
\mbox{}\verb@#endif@\\
\mbox{}\verb@@
\end{list}
\vspace{-2ex}
\end{flushleft}
\subsection{\code{std::istream\_iterator} Tests}
\subsubsection{\code{std::istream\_iterator<int>} Test}
\label{sec-code-test-istream-int}
\begin{flushleft} \small \label{part130}
\verb@"test_int_istream.cpp"@ {\footnotesize \hypertarget{270}{270} }$\equiv$
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@//test_int.cpp version 1.0@\\
\mbox{}\verb@#include <iostream>@\\
\mbox{}\verb@#include <fstream>@\\
\mbox{}\verb@#include <ctype.h>@\\
\mbox{}\verb@#include "router.hpp"@\\
\mbox{}\verb@using std::cout;@\\
\mbox{}\verb@using std::endl;@\\
\mbox{}\verb@using std::vector;@\\
\mbox{}\verb@using std::back_inserter;@\\
\mbox{}\verb@using std::istream_iterator;@\\
\mbox{}\verb@using std::back_insert_iterator;@\\
\mbox{}\verb@using std::cin;@\\
\mbox{}\verb@@\\
\mbox{}\verb@using gdfa::router;@\\
\mbox{}\verb@using gdfa::destination;@\\
\mbox{}\verb@@\\
\mbox{}\verb@bool validate(vector<int> sorted[]);@\\
\mbox{}\verb@@\\
\mbox{}\verb@template<typename output_iterator>@\\
\mbox{}\verb@class range_checker : public destination<int>@\\
\mbox{}\verb@{@\\
\mbox{}\verb@   private:@\\
\mbox{}\verb@  output_iterator m_out;@\\
\mbox{}\verb@  int m_lower;@\\
\mbox{}\verb@                        int m_upper; @\\
\mbox{}\verb@  @\\
\mbox{}\verb@   public:@\\
\mbox{}\verb@  range_checker(output_iterator out, int lower,int upper)@\\
\mbox{}\verb@         : m_out(out), m_lower(lower), m_upper(upper) {}@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  /*out distribute function checks the first letter to see if it is@\\
\mbox{}\verb@  the same as in the predicate*/@\\
\mbox{}\verb@  bool distribute(const int& element)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@     if(m_lower < element && m_upper > element)@\\
\mbox{}\verb@     {@\\
\mbox{}\verb@    *m_out++ = element;@\\
\mbox{}\verb@    return true;@\\
\mbox{}\verb@     }@\\
\mbox{}\verb@     @\\
\mbox{}\verb@     return false;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@};@\\
\mbox{}\verb@@\\
\mbox{}\verb@template<typename output_iterator>@\\
\mbox{}\verb@class my_default : public destination<int>@\\
\mbox{}\verb@{@\\
\mbox{}\verb@   private:@\\
\mbox{}\verb@  output_iterator m_out;@\\
\mbox{}\verb@   public:@\\
\mbox{}\verb@  my_default(output_iterator out)@\\
\mbox{}\verb@         : m_out(out) {}@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  bool distribute(const int& n)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@     *m_out++ = n;@\\
\mbox{}\verb@     return true;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@};@\\
\mbox{}\verb@@\\
\mbox{}\verb@int main(int argc,char *argv[])@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  cout << "\n\n\nTest:  test_int_istream.cpp"@\\
\mbox{}\verb@    << "\n\nTest Uses istream iterator and type int as input.\n"@\\
\mbox{}\verb@    << "***********************************\n\n"@\\
\mbox{}\verb@    << "Results:\n\n";@\\
\mbox{}\verb@@\\
\mbox{}\verb@  router<int> r;@\\
\mbox{}\verb@  vector<int> sorted[11];//one for each letter, one for default@\\
\mbox{}\verb@  range_checker<back_insert_iterator<vector<int> > > *dummy[10];@\\
\mbox{}\verb@  int lower = 0;@\\
\mbox{}\verb@  int upper = 100000;@\\
\mbox{}\verb@  for(int i = 0; i<10;i++)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    dummy[i] =@\\
\mbox{}\verb@     new range_checker<back_insert_iterator<vector<int> > >@\\
\mbox{}\verb@     (back_inserter(sorted[i]), lower, upper);@\\
\mbox{}\verb@    r.add_destination(*dummy[i]);@\\
\mbox{}\verb@    lower+= 100000;@\\
\mbox{}\verb@    upper+= 100000;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  my_default<back_insert_iterator<vector<int> > >@\\
\mbox{}\verb@   dflt(back_inserter(sorted[10]));@\\
\mbox{}\verb@  r.set_default(dflt);@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  typedef istream_iterator<int> int_in;@\\
\mbox{}\verb@  r.distribute(int_in(cin),int_in());@\\
\mbox{}\verb@  cout<<"number of elements in each range, with the max and min ";@\\
\mbox{}\verb@  cout<<"element in the ranges"<<endl;@\\
\mbox{}\verb@  for(int i = 0;i<10;i++)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    cout<<"("<<i * 100000<<","<<(i+1)*100000<<"): ";@\\
\mbox{}\verb@    cout<<sorted[i].size()<<" ";@\\
\mbox{}\verb@    cout<<*max_element(sorted[i].begin(),sorted[i].end())@\\
\mbox{}\verb@      <<" "<<*min_element(sorted[i].begin(),sorted[i].end())<<endl;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  cout<<"Number elements caught by default case: ";@\\
\mbox{}\verb@  cout<<sorted[10].size()<<endl;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  if(validate(sorted))@\\
\mbox{}\verb@    cout<<"Passed Validation Test"<<endl;@\\
\mbox{}\verb@  else@\\
\mbox{}\verb@    cout<<"Failed Validation Test"<<endl;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  cout<<"\n*************     END OF RESULTS     ";@\\
\mbox{}\verb@  cout<<"*************\n\n";@\\
\mbox{}\verb@@\\
\mbox{}\verb@  return 0;@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@bool validate(vector<int> sorted[])@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  int i;@\\
\mbox{}\verb@  int j = 0;@\\
\mbox{}\verb@  for(i = 0,j=0;i<10;i++,j+=100000)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    int min = *min_element(sorted[i].begin(),sorted[i].end());@\\
\mbox{}\verb@    if(j>=min)@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      cout<<"Failed, "<<min<<" is not in range ("<<j<<",";@\\
\mbox{}\verb@      cout<<j+100000<<")"<<endl;@\\
\mbox{}\verb@      return false;@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@    double max = *max_element(sorted[i].begin(),sorted[i].end());@\\
\mbox{}\verb@    if(j+100000 <= max)@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      cout<<"Failed, "<<max<<" is not in range ("<<j<<",";@\\
\mbox{}\verb@      cout<<j+100000<<")"<<endl;@\\
\mbox{}\verb@      return false;@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  return true;@\\
\mbox{}\verb@@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@
\end{list}
\vspace{-2ex}
\end{flushleft}
\subsubsection{\code{std::istream\_iterator<double>} Test}
\label{sec-code-test-istream-double}
\begin{flushleft} \small \label{part131}
\verb@"test_double_istream.cpp"@ {\footnotesize \hypertarget{273}{273} }$\equiv$
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@//test_double.cpp version 1.0@\\
\mbox{}\verb@#include <iostream>@\\
\mbox{}\verb@#include <fstream>@\\
\mbox{}\verb@#include <ctype.h>@\\
\mbox{}\verb@#include <algorithm>@\\
\mbox{}\verb@#include "router.hpp"@\\
\mbox{}\verb@using std::cout;@\\
\mbox{}\verb@using std::endl;@\\
\mbox{}\verb@using std::vector;@\\
\mbox{}\verb@using std::back_inserter;@\\
\mbox{}\verb@using std::istream_iterator;@\\
\mbox{}\verb@using std::back_insert_iterator;@\\
\mbox{}\verb@using std::cin;@\\
\mbox{}\verb@using std::min_element;@\\
\mbox{}\verb@using std::max_element;@\\
\mbox{}\verb@using gdfa::router;@\\
\mbox{}\verb@using gdfa::destination;@\\
\mbox{}\verb@@\\
\mbox{}\verb@bool validate(vector<double> sorted[]);@\\
\mbox{}\verb@@\\
\mbox{}\verb@class my_compare@\\
\mbox{}\verb@{@\\
\mbox{}\verb@public:@\\
\mbox{}\verb@  my_compare() {}@\\
\mbox{}\verb@  static const double epsilon = 1e-10;@\\
\mbox{}\verb@  bool less(const double &lhs,const double &rhs)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    if((rhs - lhs) < epsilon) return false;@\\
\mbox{}\verb@    if(lhs<rhs) return true;@\\
\mbox{}\verb@    return false;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  bool greater(const double &lhs,const double &rhs)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    if((lhs - rhs) < epsilon) return false;@\\
\mbox{}\verb@    if(lhs>rhs) return true;@\\
\mbox{}\verb@    return false;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  bool lessequal(const double &lhs,const double &rhs)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    if((rhs - lhs) < epsilon && (rhs - lhs) > -epsilon)@\\
\mbox{}\verb@     return true;@\\
\mbox{}\verb@    if(lhs<rhs) return true;@\\
\mbox{}\verb@    return false;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  bool greaterequal(const double &lhs,const double &rhs)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    if((lhs - rhs) < epsilon && (lhs - rhs) > -epsilon)@\\
\mbox{}\verb@     return true;@\\
\mbox{}\verb@    if(lhs>rhs) return true;@\\
\mbox{}\verb@    return false;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  bool equal(const double &lhs,const double &rhs)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    if((lhs - rhs) < epsilon && (rhs - lhs) < -epsilon)@\\
\mbox{}\verb@     return true;@\\
\mbox{}\verb@    if((rhs -lhs) < epsilon && (lhs - rhs) < -epsilon)@\\
\mbox{}\verb@     return true;@\\
\mbox{}\verb@    return false;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@@\\
\mbox{}\verb@};@\\
\mbox{}\verb@@\\
\mbox{}\verb@my_compare comp;@\\
\mbox{}\verb@@\\
\mbox{}\verb@template<typename output_iterator>@\\
\mbox{}\verb@class range_checker : public destination<double>@\\
\mbox{}\verb@{@\\
\mbox{}\verb@   private:@\\
\mbox{}\verb@      output_iterator m_out;@\\
\mbox{}\verb@      double m_lower;@\\
\mbox{}\verb@      double m_upper;@\\
\mbox{}\verb@//      static my_compare comp;@\\
\mbox{}\verb@      @\\
\mbox{}\verb@   public:@\\
\mbox{}\verb@      range_checker(output_iterator out, double lower,double upper)@\\
\mbox{}\verb@                 : m_out(out), m_lower(lower), m_upper(upper) {}@\\
\mbox{}\verb@      @\\
\mbox{}\verb@      /*out distribute function checks the first letter to see if@\\
\mbox{}\verb@      it is the same as in the predicate*/@\\
\mbox{}\verb@      bool distribute(const double& element)@\\
\mbox{}\verb@      {@\\
\mbox{}\verb@        if(comp.greater(element,m_lower) &&@\\
\mbox{}\verb@           comp.less(element,m_upper))@\\
\mbox{}\verb@        {@\\
\mbox{}\verb@            if( element < .3000000001 && element > .29999999)@\\
\mbox{}\verb@            {@\\
\mbox{}\verb@              cout<<"dumber than dirt "<<element<<endl;@\\
\mbox{}\verb@              cout<<element - m_lower<<endl;@\\
\mbox{}\verb@/*              if((element - m_lower) > epsilon)@\\
\mbox{}\verb@                cout<<"greater"<<endl;@\\
\mbox{}\verb@              if((m_lower - element) > epsilon)@\\
\mbox{}\verb@                cout<<"less than"<<endl;*/@\\
\mbox{}\verb@            }@\\
\mbox{}\verb@            *m_out++ = element;@\\
\mbox{}\verb@            return true;@\\
\mbox{}\verb@         }@\\
\mbox{}\verb@         @\\
\mbox{}\verb@         return false;@\\
\mbox{}\verb@      }@\\
\mbox{}\verb@};@\\
\mbox{}\verb@@\\
\mbox{}\verb@template<typename output_iterator>@\\
\mbox{}\verb@class my_default : public destination<double>@\\
\mbox{}\verb@{@\\
\mbox{}\verb@   private:@\\
\mbox{}\verb@      output_iterator m_out;@\\
\mbox{}\verb@   public:@\\
\mbox{}\verb@      my_default(output_iterator out)@\\
\mbox{}\verb@                 : m_out(out) {}@\\
\mbox{}\verb@      @\\
\mbox{}\verb@      bool distribute(const double& n)@\\
\mbox{}\verb@      {@\\
\mbox{}\verb@         *m_out++ = n;@\\
\mbox{}\verb@         return true;@\\
\mbox{}\verb@      }@\\
\mbox{}\verb@};@\\
\mbox{}\verb@@\\
\mbox{}\verb@int main(int argc,char *argv[])@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  cout << "\n\n\nTest:  test_double_istream.cpp"@\\
\mbox{}\verb@    << "\n\nTest Uses istream iterator and type double as input.\n"@\\
\mbox{}\verb@    << "***********************************\n\n"@\\
\mbox{}\verb@    << "Results:\n\n";@\\
\mbox{}\verb@@\\
\mbox{}\verb@  router<double> r;@\\
\mbox{}\verb@  vector<double> sorted[11];//one for each letter, one for default@\\
\mbox{}\verb@  range_checker<back_insert_iterator<vector<double> > > *dummy[10];@\\
\mbox{}\verb@  double lower = 0.0;@\\
\mbox{}\verb@  double upper = 0.1;@\\
\mbox{}\verb@  for(int i = 0; i<10;i++)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    dummy[i] =@\\
\mbox{}\verb@     new range_checker<back_insert_iterator<vector<double> > >@\\
\mbox{}\verb@     (back_inserter(sorted[i]), lower, upper);@\\
\mbox{}\verb@    r.add_destination(*dummy[i]);@\\
\mbox{}\verb@    lower+= 0.1;@\\
\mbox{}\verb@    upper+= 0.1;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  my_default<back_insert_iterator<vector<double> > >@\\
\mbox{}\verb@   dflt(back_inserter(sorted[10]));@\\
\mbox{}\verb@  r.set_default(dflt);@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  typedef istream_iterator<double> double_in;@\\
\mbox{}\verb@  r.distribute(double_in(cin),double_in());@\\
\mbox{}\verb@  cout<<"number of elements in each range, with the max and min ";@\\
\mbox{}\verb@  cout<<"element in the ranges"<<endl;@\\
\mbox{}\verb@  double j;@\\
\mbox{}\verb@  int i;@\\
\mbox{}\verb@  for(i = 0,j = 0.0;i<10;i++,j+=.1)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    cout<<"("<<j<<","<<j+.1<<"): "<<sorted[i].size()<<" ";@\\
\mbox{}\verb@    cout<<*max_element(sorted[i].begin(),sorted[i].end())@\\
\mbox{}\verb@      <<" "<<*min_element(sorted[i].begin(),sorted[i].end())<<endl;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  cout<<"Number of elements caught by default case: ";@\\
\mbox{}\verb@  cout<<sorted[10].size()<<endl;@\\
\mbox{}\verb@  if(validate(sorted))@\\
\mbox{}\verb@    cout<<"Passed Validation Test"<<endl;@\\
\mbox{}\verb@  else@\\
\mbox{}\verb@    cout<<"Failed Validation Test"<<endl;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  cout<<"\n*************     END OF RESULTS     ";@\\
\mbox{}\verb@  cout<<"*************\n\n";@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@  return 0;@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@bool validate(vector<double> sorted[])@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  int i;@\\
\mbox{}\verb@  double j;@\\
\mbox{}\verb@  for(i = 0,j = 0.0;i<10;i++,j+=.1)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    double min = *min_element(sorted[i].begin(),sorted[i].end());@\\
\mbox{}\verb@    if(comp.greaterequal(j,min))@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      cout<<"Failed, "<<min<<" is not in range ("<<j<<","<<j+.1;@\\
\mbox{}\verb@      cout<<")"<<endl;@\\
\mbox{}\verb@      return false;@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@    double max = *max_element(sorted[i].begin(),sorted[i].end());@\\
\mbox{}\verb@    if(comp.lessequal(j+.1,max))@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      cout<<"Failed, "<<max<<" is not in range ("<<j<<","<<j+.1;@\\
\mbox{}\verb@      cout<<")"<<endl;@\\
\mbox{}\verb@      return false;@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  return true;@\\
\mbox{}\verb@@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@
\end{list}
\vspace{-2ex}
\end{flushleft}
\subsubsection{\code{std::istream\_iterator<char>} Test}
\label{sec-code-test-istream-char}
\begin{flushleft} \small \label{part132}
\verb@"test_char_istream.cpp"@ {\footnotesize \hypertarget{277}{277} }$\equiv$
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@//test_char_istream.cpp version 1.0@\\
\mbox{}\verb@#include <iostream>@\\
\mbox{}\verb@#include <fstream>@\\
\mbox{}\verb@#include <string>@\\
\mbox{}\verb@#include <ctype.h>@\\
\mbox{}\verb@#include "router.hpp"@\\
\mbox{}\verb@using std::cout;@\\
\mbox{}\verb@using std::endl;@\\
\mbox{}\verb@using std::vector;@\\
\mbox{}\verb@using std::back_inserter;@\\
\mbox{}\verb@using std::istream_iterator;@\\
\mbox{}\verb@using std::back_insert_iterator;@\\
\mbox{}\verb@using std::string;@\\
\mbox{}\verb@using std::cin;@\\
\mbox{}\verb@@\\
\mbox{}\verb@using gdfa::router;@\\
\mbox{}\verb@using gdfa::destination;@\\
\mbox{}\verb@@\\
\mbox{}\verb@bool validate(vector<char> sorted[]);@\\
\mbox{}\verb@@\\
\mbox{}\verb@template<typename output_iterator>@\\
\mbox{}\verb@class word_sorter : public destination<char>@\\
\mbox{}\verb@{@\\
\mbox{}\verb@   private:@\\
\mbox{}\verb@  output_iterator m_out;@\\
\mbox{}\verb@  char m_first_letter;@\\
\mbox{}\verb@  @\\
\mbox{}\verb@   public:@\\
\mbox{}\verb@  word_sorter(output_iterator out, char first_letter)@\\
\mbox{}\verb@         : m_out(out), m_first_letter(first_letter) {}@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  /*out distribute function checks the first letter to see if it is@\\
\mbox{}\verb@  the same as in the predicate*/@\\
\mbox{}\verb@  bool distribute(const char& element)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@     if (tolower((const int)element) == m_first_letter)@\\
\mbox{}\verb@     {@\\
\mbox{}\verb@    *m_out++ = element;@\\
\mbox{}\verb@    return true;@\\
\mbox{}\verb@     }@\\
\mbox{}\verb@     @\\
\mbox{}\verb@     return false;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@};@\\
\mbox{}\verb@@\\
\mbox{}\verb@template<typename output_iterator>@\\
\mbox{}\verb@class my_default : public destination<char>@\\
\mbox{}\verb@{@\\
\mbox{}\verb@   private:@\\
\mbox{}\verb@  output_iterator m_out;@\\
\mbox{}\verb@   public:@\\
\mbox{}\verb@  my_default(output_iterator out)@\\
\mbox{}\verb@         : m_out(out) {}@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  bool distribute(const char& n)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@     *m_out++ = n;@\\
\mbox{}\verb@     return true;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@};@\\
\mbox{}\verb@@\\
\mbox{}\verb@int main(int argc,char *argv[])@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  cout << "\n\n\nTest:  test_char_istream.cpp"@\\
\mbox{}\verb@    << "\n\nTest Uses istream iterator and type char as input.\n"@\\
\mbox{}\verb@    << "***********************************\n\n"@\\
\mbox{}\verb@    << "Results:\n\n";@\\
\mbox{}\verb@@\\
\mbox{}\verb@  router<char> r;@\\
\mbox{}\verb@  vector<char> sorted[27];//one for each letter, one for default@\\
\mbox{}\verb@  word_sorter<back_insert_iterator<vector<char> > > *dummy[26];@\\
\mbox{}\verb@  for(int i = 0; i<26;i++)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    dummy[i] =@\\
\mbox{}\verb@     new word_sorter<back_insert_iterator<vector<char> > >@\\
\mbox{}\verb@     (back_inserter(sorted[i]),(char)(i + 97));@\\
\mbox{}\verb@    r.add_destination(*dummy[i]);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  my_default<back_insert_iterator<vector<char> > >@\\
\mbox{}\verb@   dflt(back_inserter(sorted[26]));@\\
\mbox{}\verb@  r.set_default(dflt);@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  typedef istream_iterator<char> char_in;@\\
\mbox{}\verb@  r.distribute(char_in(cin),char_in());@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  for(int i = 0;i<26;i++)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    cout<<(char)(i + 97)<<": "<<sorted[i].size()<<endl;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  cout<<"Number of elements caught by default case: ";@\\
\mbox{}\verb@  cout<<sorted[26].size()<<endl;@\\
\mbox{}\verb@  if(validate(sorted))@\\
\mbox{}\verb@    cout<<"Passed Validation Test"<<endl;@\\
\mbox{}\verb@  else@\\
\mbox{}\verb@    cout<<"Failed Validation Test"<<endl;@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@  cout<<"\n*************     END OF RESULTS     ";@\\
\mbox{}\verb@  cout<<"*************\n\n";@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@  return 0;@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@\\
\mbox{}\verb@bool validate(vector<char> sorted[])@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  vector<char>::iterator iter;@\\
\mbox{}\verb@  for(int i = 0;i<26;i++)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    iter = sorted[i].begin();@\\
\mbox{}\verb@    for(;iter != sorted[i].end();iter++)@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      //we want to check vs lowercase chars@\\
\mbox{}\verb@      if(tolower((int)*iter) != (char)(i + 97))@\\
\mbox{}\verb@      {@\\
\mbox{}\verb@        cout<<"Wrong letter: "<<*iter<<" should be ";@\\
\mbox{}\verb@        cout<<(char)(i + 97)<<" "<<i<<endl;@\\
\mbox{}\verb@        return false;@\\
\mbox{}\verb@        break;@\\
\mbox{}\verb@      }@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  iter = sorted[26].begin();@\\
\mbox{}\verb@  for(;iter != sorted[26].end();iter++)//check default case@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    //we want to check vs lowercase chars@\\
\mbox{}\verb@    if(tolower((int)*iter) > 96 && tolower((int)*iter) < 123)@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@  cout<<"Wrong letter: "<<*iter<<" should not be in default case";@\\
\mbox{}\verb@  cout<<endl;@\\
\mbox{}\verb@  return false;@\\
\mbox{}\verb@  break;@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  return true;@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@
\end{list}
\vspace{-2ex}
\end{flushleft}
\subsubsection{\code{std::istream\_iterator<std::string>} Test}
\label{sec-code-test-istream-string}
\begin{flushleft} \small \label{part133}
\verb@"test_string_istream.cpp"@ {\footnotesize \hypertarget{280}{280} }$\equiv$
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@//test_string.cpp version 1.0@\\
\mbox{}\verb@#include <iostream>@\\
\mbox{}\verb@#include <fstream>@\\
\mbox{}\verb@#include <string>@\\
\mbox{}\verb@#include <ctype.h>@\\
\mbox{}\verb@#include "test_classes.hpp"@\\
\mbox{}\verb@#include "router.hpp"@\\
\mbox{}\verb@using std::cout;@\\
\mbox{}\verb@using std::endl;@\\
\mbox{}\verb@using std::vector;@\\
\mbox{}\verb@using std::back_inserter;@\\
\mbox{}\verb@using std::istream_iterator;@\\
\mbox{}\verb@using std::back_insert_iterator;@\\
\mbox{}\verb@using std::string;@\\
\mbox{}\verb@using std::cin;@\\
\mbox{}\verb@@\\
\mbox{}\verb@using gdfa::router;@\\
\mbox{}\verb@using gdfa::destination;@\\
\mbox{}\verb@@\\
\mbox{}\verb@bool validate(vector<string> sorted[]);@\\
\mbox{}\verb@@\\
\mbox{}\verb@int main(int argc,char *argv[])@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  cout << "\n\n\nTest:  test_string_istream.cpp"@\\
\mbox{}\verb@    << "\n\nTest Uses istream iterator and type string as input.\n"@\\
\mbox{}\verb@    << "***********************************\n\n"@\\
\mbox{}\verb@    << "Results:\n\n";@\\
\mbox{}\verb@@\\
\mbox{}\verb@  router<string> r;@\\
\mbox{}\verb@  vector<string> sorted[27];//one for each letter, one for default@\\
\mbox{}\verb@  word_sorter<back_insert_iterator<vector<string> > > *dummy[26];@\\
\mbox{}\verb@  for(int i = 0; i<26;i++)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    dummy[i] =@\\
\mbox{}\verb@     new word_sorter<back_insert_iterator<vector<string> > >@\\
\mbox{}\verb@     (back_inserter(sorted[i]),(char)(i + 97));@\\
\mbox{}\verb@    r.add_destination(*dummy[i]);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  my_default<back_insert_iterator<vector<string> > >@\\
\mbox{}\verb@   dflt(back_inserter(sorted[26]));@\\
\mbox{}\verb@  r.set_default(dflt);@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  typedef istream_iterator<string> string_in;@\\
\mbox{}\verb@  r.distribute(string_in(cin),string_in());@\\
\mbox{}\verb@  @\\
\mbox{}\verb@  for(int i = 0;i<26;i++)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    cout<<(char)(i + 97)<<": "<<sorted[i].size()<<endl;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  cout<<"Number of elements caught by default case: ";@\\
\mbox{}\verb@  cout<<sorted[26].size()<<endl;@\\
\mbox{}\verb@  if(validate(sorted))@\\
\mbox{}\verb@    cout<<"Passed Validation Test"<<endl;@\\
\mbox{}\verb@  else@\\
\mbox{}\verb@    cout<<"Failed Validation Test"<<endl;@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@  cout << "\n*************     END OF RESULTS     ";@\\
\mbox{}\verb@  cout<<"*************\n\n";@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@  return 0;@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@\\
\mbox{}\verb@@\\
\mbox{}\verb@bool validate(vector<string> sorted[])@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  vector<string>::iterator iter;@\\
\mbox{}\verb@  for(int i = 0;i<26;i++)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    iter = sorted[i].begin();@\\
\mbox{}\verb@    for(;iter != sorted[i].end();iter++)@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      //need to make sure that we are checking case insensitive@\\
\mbox{}\verb@      if(tolower((int)(*iter)[0]) != (char)(i + 97))@\\
\mbox{}\verb@      {@\\
\mbox{}\verb@        cout<<"Wrong letter: "<<*iter<<" should be ";@\\
\mbox{}\verb@        cout<<(char)(i + 97)<<" "<<i<<endl;@\\
\mbox{}\verb@        return false;@\\
\mbox{}\verb@        break;@\\
\mbox{}\verb@      }@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  iter = sorted[26].begin();@\\
\mbox{}\verb@  for(;iter != sorted[26].end();iter++)//check default case@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    //we want to check vs lowercase chars@\\
\mbox{}\verb@    if(tolower((int)(*iter)[0]) > 96@\\
\mbox{}\verb@       && tolower((int)(*iter)[0]) < 123)@\\
\mbox{}\verb@    {@\\
\mbox{}\verb@      cout<<"Wrong letter: "<<*iter;@\\
\mbox{}\verb@      cout<<" should not be in default case"<<endl;@\\
\mbox{}\verb@      return false;@\\
\mbox{}\verb@      break;@\\
\mbox{}\verb@    }@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  return true;@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@
\end{list}
\vspace{-2ex}
\end{flushleft}
\subsection{Boundary Conditions Tests}
\subsubsection{Test with no \code{destination}s}
\label{sec-code-test-no-destinations}
\begin{flushleft} \small \label{part134}
\verb@"nodestinations.cpp"@ {\footnotesize \hypertarget{282}{282} }$\equiv$
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@//testnodestinations.cpp version 1.1@\\
\mbox{}\verb@#include "router.hpp"@\\
\mbox{}\verb@#include "test_classes.hpp"@\\
\mbox{}\verb@#include <iostream>@\\
\mbox{}\verb@#include <vector>@\\
\mbox{}\verb@#include <iterator>@\\
\mbox{}\verb@@\\
\mbox{}\verb@using std::cout;@\\
\mbox{}\verb@using std::endl;@\\
\mbox{}\verb@using std::vector;@\\
\mbox{}\verb@using std::back_inserter;@\\
\mbox{}\verb@using std::istream_iterator;@\\
\mbox{}\verb@using std::back_insert_iterator;@\\
\mbox{}\verb@using std::string;@\\
\mbox{}\verb@using std::cin;@\\
\mbox{}\verb@@\\
\mbox{}\verb@int main()@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  cout << "\n\n\nTest:  nodestinations.cpp\n\n"@\\
\mbox{}\verb@    << "Test router without adding and destinations to it.\n"@\\
\mbox{}\verb@    << "**************************************************\n\n"@\\
\mbox{}\verb@    << "Results:\n\n";@\\
\mbox{}\verb@@\\
\mbox{}\verb@  router<string> r;@\\
\mbox{}\verb@  typedef istream_iterator<string> in_string;@\\
\mbox{}\verb@  r.distribute(in_string(cin),in_string());@\\
\mbox{}\verb@@\\
\mbox{}\verb@  cout << "\n*************     END OF RESULTS     ";@\\
\mbox{}\verb@  cout<<"*************\n\n";@\\
\mbox{}\verb@@\\
\mbox{}\verb@  return 0;@\\
\mbox{}\verb@@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@
\end{list}
\vspace{-2ex}
\end{flushleft}
\subsubsection{Test with no Input}
\label{sec-code-test-no-input}
\begin{flushleft} \small \label{part135}
\verb@"noinput.cpp"@ {\footnotesize \hypertarget{283}{283} }$\equiv$
\vspace{-1ex}
\begin{list}{}{} \item
\mbox{}\verb@//noinput.cpp version 1.1@\\
\mbox{}\verb@#include <iostream>@\\
\mbox{}\verb@#include <fstream>@\\
\mbox{}\verb@#include <string>@\\
\mbox{}\verb@#include <ctype.h>@\\
\mbox{}\verb@#include "router.hpp"@\\
\mbox{}\verb@#include "test_classes.hpp"@\\
\mbox{}\verb@using std::cout;@\\
\mbox{}\verb@using std::endl;@\\
\mbox{}\verb@using std::vector;@\\
\mbox{}\verb@using std::back_inserter;@\\
\mbox{}\verb@using std::istream_iterator;@\\
\mbox{}\verb@using std::back_insert_iterator;@\\
\mbox{}\verb@using std::string;@\\
\mbox{}\verb@using std::cin;@\\
\mbox{}\verb@@\\
\mbox{}\verb@using gdfa::router;@\\
\mbox{}\verb@using gdfa::destination;@\\
\mbox{}\verb@@\\
\mbox{}\verb@int main(int argc,char *argv[])@\\
\mbox{}\verb@{@\\
\mbox{}\verb@  cout << "\n\n\nTest:  noinput.cpp\n\n"@\\
\mbox{}\verb@    << "Test behavior of router on an empty input range.\n"@\\
\mbox{}\verb@    << "********************************************\n\n"@\\
\mbox{}\verb@    << "Results:\n\n";@\\
\mbox{}\verb@@\\
\mbox{}\verb@  router<string> r;@\\
\mbox{}\verb@  vector<string> sorted[27];//one for each letter, one for default@\\
\mbox{}\verb@  word_sorter<back_insert_iterator<vector<string> > > *dummy[26];@\\
\mbox{}\verb@  for(int i = 0; i<26;i++)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    dummy[i] =@\\
\mbox{}\verb@     new word_sorter<back_insert_iterator<vector<string> > >@\\
\mbox{}\verb@     (back_inserter(sorted[i]),(char)(i + 97));@\\
\mbox{}\verb@    r.add_destination(*dummy[i]);@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  my_default<back_insert_iterator<vector<string> > >@\\
\mbox{}\verb@   dflt(back_inserter(sorted[26]));@\\
\mbox{}\verb@  r.set_default(dflt);@\\
\mbox{}\verb@  typedef istream_iterator<string> in_string;@\\
\mbox{}\verb@  r.distribute(in_string(),in_string());@\\
\mbox{}\verb@@\\
\mbox{}\verb@  for(int i = 0;i<26;i++)@\\
\mbox{}\verb@  {@\\
\mbox{}\verb@    cout<<(char)(i + 97)<<": "<<sorted[i].size()<<endl;@\\
\mbox{}\verb@  }@\\
\mbox{}\verb@  cout<<"Default: "<<sorted[26].size()<<endl<<endl;@\\
\mbox{}\verb@@\\
\mbox{}\verb@  cout << "\n*************     END OF RESULTS     ";@\\
\mbox{}\verb@  cout<<"*************\n\n";@\\
\mbox{}\verb@@\\
\mbox{}\verb@    return 0;@\\
\mbox{}\verb@}@\\
\mbox{}\verb@@
\end{list}
\vspace{-2ex}
\end{flushleft}
\begin{thebibliography}{9}

\bibitem{opcounting} G.J. Derge, D.R. Musser, `` Operation Counting 
Adaptors for the C++ Standard Template Library,'' 
http://www.cs.rpi.edu/~musser/gsd/opcount/opcount-full-report.pdf. 
Online available.

\bibitem{dickens} C. Dickens, ``A Christmas Carol,'' \emph{Project 
Gutenberg Etext}, 
http://www.ibiblio.org/gutenberg/etext92/carol10.txt, Project 
Gutenberg, - Urbana, Illinois (USA) (December 1992)

\bibitem{drm-book} D. Musser, et al., \emph{STL Tutorial and 
Reference Guide, Second Edition: C++ Programming with the Standard 
Template Library} Addison-Wesley, Boston, MA, 2001, ISBN 
0-201-37923-6.

\bibitem{sgi-stl} ``Standard Template Library Programmer's Guide,'' 
http://www.sgi.com/tech/stl. Online available.

\end{thebibliography}
\end{document}
