%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
%%
%%  base_matrix.tex       LiDIA documentation
%%
%%  This file contains the documentation of the class base_matrix
%%
%%  Copyright   (c)   1995   by  LiDIA-Group
%%
%%  Authors: Patrick Theobald
%%

%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%

\NAME

\CLASS{base_matrix< T >} \dotfill parameterized base matrix class


%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%

\ABSTRACT

The class \code{base_matrix< T >} allows to order elements of type \code{T} which is allowed to
be either a built-in type or a class in form of a matrix.
\begin{displaymath}
  A = (a_{i,j}) \in T^{m \times n} \enspace,
\end{displaymath}
where $0 \leq i < m$ and $0 \leq j < n$.  It allows to create matrices and offers elementary
access functions.


%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%

\DESCRIPTION

A variable of type \code{base_matrix< T >} consists of a 2-dimensional array \code{T** value}
and two elements (\code{rows, columns}) of type \code{lidia_size_t} which store the number of
rows and columns of the matrix, respectively.  Additionally a variable of type
\code{base_matrix< T >} contains two unsigned integers (\code{print_mode}, (\code{print_mode}).
The member \code{print_mode} determines in which format the matrix will be printed.  The member
\code{lattice_mode} stores informations used by the lattice classes.

In the following descriptions we use \code{$A$.rows} to label the number of rows and
\code{$A$.columns} to label the number of columns of the matrix $A$.


%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%

\CONS

If $a \leq 0$ or $b \leq 0$ or $v = \code{NULL}$ in one of the following constructors, the \LEH
will be invoked.

\begin{fcode}{ct}{base_matrix< T >}{}
  constructs a $1 \times 1$ matrix initialized with values generated by the default constructor
  of type \code{T}.
\end{fcode}

\begin{fcode}{ct}{base_matrix< T >}{lidia_size_t $a$, lidia_size_t $b$}
  constructs an $a \times b$ matrix initialized with values generated by the default constructor
  of type \code{T}.
\end{fcode}

\begin{fcode}{ct}{base_matrix< T >}{lidia_size_t $a$, lidia_size_t $b$, const T ** $v$}
  constructs an $a \times b$ matrix initialized with the values of the 2-dimensional array $v$.
  The behaviour of this constructor is undefined if the array $v$ has less than $a$ rows or less
  than $b$ columns.
\end{fcode}

\begin{fcode}{ct}{base_matrix< T >}{const base_matrix< T > & $A$}
  constructs a copy of matrix $A$.
\end{fcode}

\begin{fcode}{dt}{~base_matrix< T >}{}
\end{fcode}


%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%

\ASGN

Let $A$ be of type \code{base_matrix< T >}.  The operator \code{=} is overloaded.  For
efficiency reasons, the following functions are also implemented:

\begin{fcode}{void}{$A$.assign}{const base_matrix< T > & $B$}
\end{fcode}

\begin{fcode}{void}{assign}{base_matrix< T > & $A$, const base_matrix< T > & $B$}
  sets the dimensions of matrix $A$ to the dimensions of matrix $B$ and copies each entry of $B$
  to the corresponding position in $A$.
\end{fcode}


%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%

\ACCS

Let $A$ be of type \code{base_matrix< T >}.  Note that the numbering of columns and rows starts
with zero.


%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%

\SSTITLE{Access to the number of rows}

\begin{cfcode}{lidia_size_t}{$A$.get_no_of_rows}{}
  returns the number of rows of matrix $A$.
\end{cfcode}

\begin{fcode}{void}{$A$.set_no_of_rows}{lidia_size_t $k$}
  changes the number of rows of matrix $A$ into $k$.  If $k < \code{$A$.rows}$, the rows $k,
  \dots, (\code{$A$.rows} - 1)$ are discarded.  If $k > \code{$A$.rows}$, this function adds $k
  - \code{$A$.rows}$ new rows initialized with values generated by the default constructor of
  type \code{T}.  The \LEH will be invoked if $k < 1$.
\end{fcode}

%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%

\SSTITLE{Access to the number of columns}

\begin{cfcode}{lidia_size_t}{$A$.get_no_of_columns}{}
  returns the number of columns of matrix $A$.
\end{cfcode}

\begin{fcode}{void}{$A$.set_no_of_columns}{lidia_size_t $k$}
  changes the number of columns of matrix $A$ into $k$.  If $k < \code{$A$.columns}$, then the
  columns $i, \dots, (\code{$A$.columns} - 1)$ are discarded.  If $k > \code{$A$.columns}$, then
  this function adds $k - \code{$A$.columns}$ new columns initialized with values generated by
  the default-constructor for type \code{T}.  The \LEH will be invoked if $k < 1$.

\end{fcode}

%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%

\SSTITLE{Access to the number of rows and columns}

\begin{fcode}{void}{$A$.resize}{lidia_size_t $i$, lidia_size_t $j$}
  changes the number of rows into $i$ and the number of columns of matrix $A$ into $j$ by
  calling the functions \code{$A$.set_no_of_rows($i$)} and \code{$A$.set_no_of_columns($j$)}.
  The \LEH is invoked if $i < 1$ or $j < 1$.
\end{fcode}

\begin{fcode}{void}{$A$.reset}{}
  changes the number of columns and number of rows of the matrix $A$ to 1.

  Note: Memory is deallocated.
\end{fcode}

\begin{fcode}{void}{$A$.kill}{}
  changes the number of columns and number of rows of the matrix $A$ to 1.
  
  Note: Memory is deallocated.
\end{fcode}


%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%

\SSTITLE{Access to a row}

\begin{cfcode}{base_vector< T >}{$A$.operator[]}{lidia_size_t $i$}
  returns a \code{base_vector} $v$ created by copying the values of row $i$.  If $i \geq
  \code{$A$.rows}$ or $i < 0$ the \LEH will be invoked.  Note, that the size of the vector that
  is returned has $\code{$v$.size} = \code{$A$.columns}$ and $\code{$v$.capacity} =
  \code{$A$.columns}$.
\end{cfcode}

\begin{cfcode}{T *}{$A$.row}{lidia_size_t $i$}
  allocates memory and returns a copy of row $i$.  If $i \geq \code{$A$.rows}$ or $i < 0$, the
  \LEH will be invoked.
\end{cfcode}

\begin{cfcode}{T *}{$A$.get_row}{lidia_size_t $i$}
  allocates memory and returns a copy of row $i$.  If $i \geq \code{$A$.rows}$ or $i < 0$, the
  \LEH will be invoked.
\end{cfcode}

\begin{cfcode}{void}{$A$.row}{T * $v$, lidia_size_t $i$}
  copies the values of row $i$ to array $v$.  If $i \geq \code{$A$.rows}$ or $i < 0$ or $v =
  \code{NULL}$, the \LEH will be invoked.  The behaviour of this function is undefined if the
  array $v$ has less than \code{$A$.columns} elements.
\end{cfcode}

\begin{cfcode}{void}{$A$.get_row}{T * $v$, lidia_size_t $i$}
  copies the values of row $i$ to array $v$.  If $i \geq \code{$A$.rows}$ or $i < 0$ or $v =
  \code{NULL}$, the \LEH will be invoked.  The behaviour of this function is undefined if the
  array $v$ has less than \code{$A$.columns} elements.
\end{cfcode}

\begin{cfcode}{base_vector< T >}{$A$.row_vector}{lidia_size_t $i$}
  returns a \code{base_vector} $v$ created by copying the values of row $i$.  If $i \geq
  \code{$A$.rows}$ or $i < 0$ the \LEH will be invoked.  Note, that the size of the vector that
  is returned has $\code{$v$.size} = \code{$A$.columns}$ and $\code{$v$.capacity} =
  \code{$A$.columns}$.
\end{cfcode}

\begin{cfcode}{base_vector< T >}{$A$.get_row_vector}{lidia_size_t $i$}
  returns a \code{base_vector} $v$ created by copying the values of row $i$.  If $i \geq
  \code{$A$.rows}$ or $i < 0$ the \LEH will be invoked.  Note, that the size of the vector that
  is returned has $\code{$v$.size} = \code{$A$.columns}$ and $\code{$v$.capacity} =
  \code{$A$.columns}$.
\end{cfcode}

\begin{cfcode}{void}{$A$.row_vector}{base_vector< T > & $v$, lidia_size_t $i$}
  copies the values of row $i$ to \code{base_vector} $v$.  If $i \geq \code{$A$.rows}$ or $i <
  0$ the \LEH will be invoked.  Note, that the size of vector $v$ is adapted automatically.
\end{cfcode}

\begin{cfcode}{void}{$A$.get_row_vector}{base_vector< T > & $v$, lidia_size_t $i$}
  copies the values of row $i$ to \code{base_vector} $v$.  If $i \geq \code{$A$.rows}$ or $i <
  0$ the \LEH will be invoked.  Note, that the size of vector $v$ is adapted automatically.
\end{cfcode}

\begin{fcode}{void}{$A$.sto_row}{const T * $v$, lidia_size_t $j$, lidia_size_t $i$}
  stores $j$ entries of array $v$ in row $i$ of matrix $A$ starting at column zero.  If $j >
  \code{$A$.columns}$ or $j \leq 0$ or $i \geq \code{$A$.rows}$ or $i < 0$, the \LEH will be
  invoked.
\end{fcode}

\begin{fcode}{void}{$A$.sto_row_vector}{const base_vector< T > & $v$, lidia_size_t $j$, lidia_size_t $i$}
  stores $j$ entries of \code{base_vector} $v$ in row $i$ of matrix $A$ starting at column zero.
  If $j > \code{$A$.columns}$ or $j \leq 0$ or $i \geq \code{$A$.rows}$ or $i < 0$, the \LEH
  will be invoked.
\end{fcode}


%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%

\SSTITLE{Access to a column}

\begin{cfcode}{base_vector< T >}{$A$.operator()}{lidia_size_t $i$}
  returns a \code{base_vector} $v$ created by copying the values of column $i$.  If $i \geq
  \code{$A$.columns}$ or $i < 0$ the \LEH will be invoked.  Note, that the size of the vector
  that is returned has $\code{$v$.size} = \code{$A$.rows}$ and $\code{$v$.capacity} = \code{$A$.rows}$.
\end{cfcode}

\begin{cfcode}{T *}{$A$.column}{lidia_size_t $i$}
  allocates memory and returns a copy of column $i$.  If $i \geq \code{$A$.columns}$ or $i < 0$,
  the \LEH will be invoked.
\end{cfcode}

\begin{cfcode}{T *}{$A$.get_column}{lidia_size_t $i$}
  allocates memory and returns a copy of column $i$.  If $i \geq \code{$A$.columns}$ or $i < 0$,
  the \LEH will be invoked.
\end{cfcode}

\begin{cfcode}{void}{$A$.column}{T * $v$, lidia_size_t $i$}
  copies the values of column $i$ to array $v$.  If $i \geq \code{$A$.columns}$ or $i < 0$ or $v
  = \code{NULL}$, the \LEH will be invoked.  The behaviour of this function is undefined if the
  array $v$ has less than \code{$A$.rows} elements.
\end{cfcode}

\begin{cfcode}{void}{$A$.get_column}{T * $v$, lidia_size_t $i$}
  copies the values of column $i$ to array $v$.  If $i \geq \code{$A$.columns}$ or $i < 0$ or $v
  = \code{NULL}$, the \LEH will be invoked.  The behaviour of this function is undefined if the
  array $v$ has less than \code{$A$.rows} elements.
\end{cfcode}

\begin{cfcode}{base_vector< T >}{$A$.column_vector}{lidia_size_t $i$}
  returns a \code{base_vector} $v$ created by copying the values of column $i$.  If $i \geq
  \code{$A$.columns}$ or $i < 0$ the \LEH will be invoked.  Note, that the size of the vector
  that is returned has $\code{$v$.size} = \code{$A$.rows}$ and $\code{$v$.capacity} = \code{$A$.rows}$.
\end{cfcode}

\begin{cfcode}{base_vector< T >}{$A$.get_column_vector}{lidia_size_t $i$}
  returns a \code{base_vector} $v$ created by copying the values of column $i$.  If $i \geq
  \code{$A$.columns}$ or $i < 0$ the \LEH will be invoked.  Note, that the size of the vector
  that is returned has $\code{$v$.size} = \code{$A$.rows}$ and $\code{$v$.capacity} =
  \code{$A$.rows}$.
\end{cfcode}

\begin{cfcode}{void}{$A$.column_vector}{base_vector< T > & $v$, lidia_size_t $i$}
  copies the values of column $i$ to \code{base_vector} $v$.  If $i \geq \code{$A$.columns}$ or
  $i < 0$, the \LEH will be invoked.  Note, that the size of vector $v$ is adapted
  automatically.
\end{cfcode}

\begin{cfcode}{void}{$A$.get_column_vector}{base_vector< T > & $v$, lidia_size_t $i$}
  copies the values of column $i$ to \code{base_vector} $v$.  If $i \geq \code{$A$.columns}$ or
  $i < 0$, the \LEH will be invoked.  Note, that the size of vector $v$ is adapted
  automatically.
\end{cfcode}

\begin{fcode}{void}{$A$.sto_column}{const T * $v$, lidia_size_t $j$, lidia_size_t $i$}
  stores $j$ entries of array $v$ in column $i$ of matrix $A$ starting at row zero.  If $j >
  \code{$A$.rows}$ or $j \leq 0$ or $i \geq \code{$A$.columns}$ or $i < 0$, the \LEH will be
  invoked.
\end{fcode}

\begin{fcode}{void}{$A$.sto_column_vector}{const base_vector< T > & $v$, lidia_size_t $j$, lidia_size_t $i$}
  stores $j$ entries of \code{base_vector} $v$ in column $i$ of matrix $A$ starting at row zero.
  If $j > \code{$A$.rows}$ or $j \leq 0$ or $i \geq \code{$A$.columns}$ or $i < 0$, the \LEH
  will be invoked.
\end{fcode}


%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%

\SSTITLE{Access to an element}

\begin{fcode}{T &}{$A$.operator()}{lidia_size_t $i$, lidia_size_t $j$}
  returns a reference of $a_{i,j}$.  If $i \geq \code{$A$.rows}$ or $i < 0$ or $j \geq
  \code{$A$.columns}$ or $j < 0$, the \LEH will be invoked.
\end{fcode}

\begin{cfcode}{const T &}{$A$.member}{lidia_size_t $i$, lidia_size_t $j$}
  returns a constant reference of $a_{i,j}$.  If $i \geq \code{$A$.rows}$ or $i < 0$ or $j \geq
  \code{$A$.columns}$ or $j < 0$, the \LEH will be invoked.
\end{cfcode}

\begin{fcode}{void}{$A$.sto}{lidia_size_t $i$, lidia_size_t $j$, const T & $x$}
  stores $x$ as $a_{i,j}$.  If $i \geq \code{$A$.rows}$ or $i < 0$ or $j \geq
  \code{$A$.columns}$ or $j < 0$, the \LEH will be invoked.
\end{fcode}


%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%

\SSTITLE{Access to the print mode}\label{base_matrix_access}

\begin{cfcode}{unsigned long}{$A$.get_print_mode}{}
  returns the print mode for printing matrix $A$ (for further information see the description of
  Input / Output, page \pageref{base_matrix_io}).
\end{cfcode}

\begin{fcode}{void}{$A$.set_print_mode}{unsigned long $i$}
  sets the print mode for matrix $A$ to $i$ (for further information see the description of
  Input / Output, page \pageref{base_matrix_io}).
\end{fcode}


%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%

%\SSTITLE{Access to the lattice mode}

%\label{base_matrix_access}
%\begin{cfcode}{unsigned long}{$A$.get_lattice_mode}{}%
%returns the $lattice_mode$ of matrix/lattice $A$
%(for further information see the description of the lattice classes,
%page \pageref{lattice_mode}).
%\end{cfcode}

%\begin{fcode}{void}{$A$.set_lattice_mode}{unsigned long $i$}%
%sets the $lattice_mode$ for matrix $A$ to $i$
%(for further information see the description of the lattice classes,
%page \pageref{lattice_mode}).
%\end{fcode}


%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%

\SSTITLE{Access to the array of values}

\begin{cfcode}{T **}{$A$.get_data}{}
  returns a pointer to a copy of the array of values of matrix $A$.
\end{cfcode}

\begin{fcode}{void}{$A$.set_data}{const T ** $v$, lidia_size_t $r$, lidia_size_t $c$}
  sets the number of rows of matrix $A$ to $r$ and the number of columns of matrix $A$ to $c$
  and copies the values of the $(r \times c)$-array $v$ to the array of values of matrix $A$.
  The \LEH will be invoked if $r < 1$ or $c < 1$.
\end{fcode}

%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%

\STITLE{Split Functions}

Let $A$ be of type \code{base_matrix< T >}.  The following split functions allow area overlap of
the submatrices or subvectors in the following sense:

According to the dimensions of the parameters and the special scheme described in the respective
split function, the values of the member matrix are copied to the parameters.

\textbf{Example:}\\
Look at the matrix
\begin{displaymath}
  A = \begin{pmatrix}
    12 & 23 & 62 & 89 \\
    90 & 19 & 80 & 73 \\
    45 & 90 & 32 & 91
  \end{pmatrix}\enspace.
\end{displaymath}
Furthermore, let $B$ be a $(2\times 3)$-\code{base_matrix}, $C$ a $(2\times
2)$-\code{base_matrix}, $D$ a $(3\times 2)$-\code{base_matrix} and $E$ a $(3\times
3)$-\code{base_matrix}.

After executing \code{$A$.split_t($B$, $C$, $D$, $E$)} for the matrices $B$, $C$, $D$ and $E$
hold the following:
\begin{displaymath}
  \begin{array}{c}
    A = \begin{pmatrix}
      12 & 23 & 62 & 89\\
      90 & 19 & 80 & 73\\
      45 & 90 & 32 & 91
    \end{pmatrix}\\
    \text{and}\\
    B = \begin{pmatrix}
      12 & 23 & 62 \\
      90 & 19 & 80
    \end{pmatrix}\enspace, \quad
    C = \begin{pmatrix}
      62 & 89\\
      80 & 73
    \end{pmatrix}\enspace, \quad
    D = \begin{pmatrix}
      12 & 23 \\
      90 & 19 \\
      45 & 90
    \end{pmatrix}\enspace, \quad
    E = \begin{pmatrix}
      23 & 62 & 89\\
      19 & 80 & 73\\
      90 & 32 & 91
    \end{pmatrix}\enspace.
  \end{array}
\end{displaymath}
If the given conditions in the descriptions of the following functions are not satisfied, the
\LEH will be invoked.


%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%

\SSTITLE{Total split}

\begin{cfcode}{void}{$A$.split_t}{base_matrix< T > & $B$, base_matrix< T > & $C$,
    base_matrix< T > & $D$, base_matrix< T > & $E$}%
  takes matrix $A$ apart into the submatrices $B$, $C$, $D$ and $E$, with
  \begin{displaymath}
    A = \begin{pmatrix}
      B & C \\
      D & E
    \end{pmatrix}\enspace,
  \end{displaymath}
  where the following conditions have to be satisfied:
  \begin{itemize}
  \item $\code{$B$.rows}, \code{$C$.rows}, \code{$D$.rows}, \code{$E$.rows} \leq \code{$A$.rows}$;
  \item $\code{$B$.columns}, \code{$C$.columns}, \code{$D$.columns}, \code{$E$.columns} \leq
    \code{$A$.columns}$.
  \end{itemize}
\end{cfcode}


%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%

\SSTITLE{Horizontal split}

\begin{cfcode}{void}{$A$.split_h}{base_matrix< T > & $B$, base_matrix< T > & $C$}
  takes matrix $A$ apart into the submatrices $B$ and $C$, with $A = \begin{pmatrix} B & C
    \end{pmatrix}$, where the following conditions have to be satisfied:
    \begin{itemize}
    \item $\code{$B$.rows}, \code{$C$.rows} \leq \code{$A$.rows}$;
    \item $\code{$B$.columns}, \code{$C$.columns} \leq \code{$A$.columns}$.
  \end{itemize}
\end{cfcode}

\begin{cfcode}{void}{$A$.split_h}{T * $v$, base_matrix< T > & $C$}
  takes matrix $A$ apart into the array $v$ and the submatrix $C$, with $A = \begin{pmatrix} v &
    C \end{pmatrix}$, where the following conditions have to be satisfied:
  \begin{itemize}
  \item $v \neq \code{NULL}$;
  \item $\code{$C$.rows} \leq \code{$A$.rows}$;
  \item $\code{$C$.columns} \leq \code{$A$.columns}$.
  \end{itemize}
  The behaviour of this function is undefined if $v$ has less than \code{$A$.rows} elements.
\end{cfcode}

\begin{cfcode}{void}{$A$.split_h}{base_vector< T > & $v$, base_matrix< T > & $C$}
  takes matrix $A$ apart into the vector $v$ and the submatrix $C$, with $A = \begin{pmatrix} v
    & C \end{pmatrix}$, where the following conditions have to be satisfied:
  \begin{itemize}
  \item $\code{$v$.size} \leq \code{$A$.rows}$;
  \item $\code{$C$.rows} \leq \code{$A$.rows}$;
  \item $\code{$C$.columns} \leq \code{$A$.columns}$.
  \end{itemize}
\end{cfcode}

\begin{cfcode}{void}{$A$.split_h}{base_matrix< T > & $B$, T * $v$}
  takes matrix $A$ apart into the submatrix $B$ and the array $v$, with $A = \begin{pmatrix} B & v
  \end{pmatrix}$, where the following conditions have to be satisfied:
  \begin{itemize}
  \item $v \neq \code{NULL}$;
  \item $\code{$B$.rows} \leq \code{$A$.rows}$;
  \item $\code{$B$.columns} \leq \code{$A$.columns}$.
  \end{itemize}
  The behaviour of this function is undefined if $v$ has less than \code{$A$.rows} elements.
\end{cfcode}

\begin{cfcode}{void}{$A$.split_h}{base_matrix< T > & $B$, base_vector< T > & $v$}
  takes matrix $A$ apart into the submatrix $B$ and the vector $v$, with $A = \begin{pmatrix} B
    & v \end{pmatrix}$, where the following conditions have to be satisfied:
  \begin{itemize}
  \item $\code{$v$.size} \leq \code{$A$.rows}$;
  \item $\code{$B$.rows} \leq \code{$A$.rows}$;
  \item $\code{$B$.columns} \leq \code{$A$.columns}$.
  \end{itemize}
\end{cfcode}


%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%

\SSTITLE{Vertical split}

\begin{cfcode}{void}{$A$.split_v}{base_matrix< T > & $B$, base_matrix< T > & $C$}
  takes matrix $A$ apart into the submatrices $B$ and $C$, with $A = \begin{pmatrix} B \\ C
  \end{pmatrix}$, where the following conditions have to be satisfied:
  \begin{itemize}
  \item $\code{$B$.rows}, \code{$C$.rows} \leq \code{$A$.rows}$;
  \item $\code{$B$.columns}, \code{$C$.columns} \leq \code{$A$.columns}$.
  \end{itemize}
\end{cfcode}

\begin{cfcode}{void}{$A$.split_v}{T * $v$, base_matrix< T > & $C$}
  takes matrix $A$ apart into the array $v$ and the submatrix $C$, with $A = \begin{pmatrix} v \\
    C \end{pmatrix}$, where the following conditions have to be satisfied:
  \begin{itemize}
  \item $v \neq \code{NULL}$;
  \item $\code{$C$.rows} \leq \code{$A$.rows}$;
  \item $\code{$C$.columns} \leq \code{$A$.columns}$.
  \end{itemize}
  The behaviour of this function is undefined if $v$ has less than \code{$A$.columns} elements.
\end{cfcode}

\begin{cfcode}{void}{$A$.split_v}{base_vector< T > & $v$, base_matrix< T > & $C$}
  takes matrix $A$ apart into the vector $B$ and the submatrix $C$, with $A = \begin{pmatrix} v \\
    C \end{pmatrix}$, where the following conditions have to be satisfied:
  \begin{itemize}
  \item $\code{$v$.size} \leq \code{$A$.columns}$;
  \item $\code{$C$.rows} \leq \code{$A$.rows}$;
  \item $\code{$C$.columns} \leq \code{$A$.columns}$.
  \end{itemize}
\end{cfcode}

\begin{cfcode}{void}{$A$.split_v}{base_matrix< T > & $B$, T * $v$}
  takes matrix $A$ apart into the submatrix $B$ and the array $v$, with $A = \begin{pmatrix} B \\ 
    v \end{pmatrix}$, where the following conditions have to be satisfied:
  \begin{itemize}
  \item $v \neq \code{NULL}$;
  \item $\code{$B$.rows} \leq \code{$A$.rows}$;
  \item $\code{$B$.columns} \leq \code{$A$.columns}$.
  \end{itemize}
  The behaviour of this function is undefined if $v$ has less than \code{$A$.columns} elements.
\end{cfcode}

\begin{cfcode}{void}{$A$.split_v}{base_matrix< T > & $B$, base_vector< T > & $v$}
  takes matrix $A$ apart into the submatrix $B$ and the vector $v$, with $A = \begin{pmatrix} B \\
    v \end{pmatrix}$, where the following conditions have to be satisfied:
  \begin{itemize}
  \item $\code{$v$.size} \leq \code{$A$.columns}$;
  \item $\code{$B$.rows} \leq \code{$A$.rows}$;
  \item $\code{$B$.columns} \leq \code{$A$.columns}$.
  \end{itemize}
\end{cfcode}


%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%

\STITLE{Compose Functions}

Let $A$ be of type \code{base_matrix< T >}.  The following compose functions allow area overlap
of the submatrices or subvectors in the following sense:

According to the dimensions of the parameters, the order of the parameters in the prototype and
the special scheme described in the respective compose function, the values of the parameters
are copied to the member matrix.

\textbf{\large Example:}\\
Look at the matrices
\begin{displaymath}
  B = \begin{pmatrix}
    12 & 23 & 30 \\
    90 & 19 & 40
  \end{pmatrix} \enspace, \quad
  C = \begin{pmatrix}
    24 & 89\\
    67 & 73
  \end{pmatrix} \enspace, \quad
  D = \begin{pmatrix}
    21 \\
    92 \\
    45
  \end{pmatrix} \enspace, \quad
  E = \begin{pmatrix}
    12 & 88 & 73\\
    99 & 33 & 91
  \end{pmatrix}
\end{displaymath}

Further let $A$ be a $(3\times 4)$-\code{base_matrix}.  After executing \code{$A$.compose_t($B$,
  $C$, $D$, $E$)} for $A$ the following holds:
\begin{displaymath}
  A = \begin{pmatrix}
    21 & 23 & 24 & 89\\
    92 & 12 & 88 & 73\\
    45 & 99 & 33 & 91
  \end{pmatrix}
\end{displaymath}
The matrices $B$, $C$, $D$ and $E$ remain unchanged.

If the given conditions in the descriptions of the following functions are not satisfied, the
\LEH will be invoked.


%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%

\SSTITLE{Total compose}

\begin{fcode}{void}{$A$.compose_t}{const base_matrix< T > & $B$, const base_matrix< T > & $C$,
    const base_matrix< T > & $D$, const base_matrix< T > & $E$}%
  composes the matrices $B$, $C$, $D$ and $E$ to the matrix $A$, with $A = \begin{pmatrix} B & C
    \\ D & E \end{pmatrix}$, where the following conditions have to be satisfied:
  \begin{itemize}
  \item $\code{$B$.rows}, \code{$C$.rows}, \code{$D$.rows}, \code{$E$.rows} \leq
    \code{$A$.rows}$;
  \item $\code{$B$.columns}, \code{$C$.columns}, \code{$D$.columns}, \code{$E$.columns} \leq
    \code{$A$.columns}$.
  \end{itemize}
\end{fcode}


%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%

\SSTITLE{Horizontal compose}

\begin{fcode}{void}{$A$.compose_h}{const base_matrix< T > & $B$, const base_matrix< T > & $C$}
  composes the matrices $B$ and $C$ to the matrix $A$, with $A = \begin{pmatrix} B & C
  \end{pmatrix}$, where the following conditions have to be satisfied:
  \begin{itemize}
  \item $\code{$B$.rows}, \code{$C$.rows} \leq \code{$A$.rows}$;
  \item $\code{$B$.columns}, \code{$C$.columns} \leq \code{$A$.columns}$.
  \end{itemize}
\end{fcode}

\begin{fcode}{void}{$A$.compose_h}{const T * $v$, const base_matrix< T > & $C$}
  composes the array $v$ and the matrix $C$ to the matrix $A$, with
    $A = \begin{pmatrix} v & C \end{pmatrix}$, where the following conditions have to be satisfied:
  \begin{itemize}
  \item $v \neq \code{NULL}$;
  \item $\code{$C$.rows} \leq \code{$A$.rows}$;
  \item $\code{$C$.columns} \leq \code{$A$.columns}$.
  \end{itemize}
  The behaviour of this function is undefined if $v$ has less than \code{$A$.rows} elements.
\end{fcode}

\begin{fcode}{void}{$A$.compose_h}{const base_vector< T > & $v$, const base_matrix< T > & $C$}
  composes the vector $v$ and the matrix $C$ to the matrix $A$, with $A = \begin{pmatrix} v & C
  \end{pmatrix}$, where the following conditions have to be satisfied:
  \begin{itemize}
  \item $\code{$v$.size} \leq \code{$A$.rows}$;
  \item $\code{$C$.rows} \leq \code{$A$.rows}$;
  \item $\code{$C$.columns} \leq \code{$A$.columns}$.
  \end{itemize}
\end{fcode}

\begin{fcode}{void}{$A$.compose_h}{const base_matrix< T > & $B$, const T * $v$}
  composes the matrix $B$ and the array $v$ to the matrix $A$, with $A = \begin{pmatrix} B & v
  \end{pmatrix}$, where the following conditions have to be satisfied:
  \begin{itemize}
  \item $v \neq \code{NULL}$;
  \item $\code{$B$.rows} \leq \code{$A$.rows}$;
  \item $\code{$B$.columns} \leq \code{$A$.columns}$.
  \end{itemize}
  The behaviour of this function is undefined if $v$ has less than \code{$A$.rows} elements.
\end{fcode}

\begin{fcode}{void}{$A$.compose_h}{const base_matrix< T > & $B$, const base_vector< T > & $v$}
  composes the matrix $B$ and the vector $v$ to the matrix $A$, with $A = \begin{pmatrix} B & v
  \end{pmatrix}$, where the following conditions have to be satisfied:
  \begin{itemize}
  \item $\code{$v$.size} \leq \code{$A$.rows}$;
  \item $\code{$B$.rows} \leq \code{$A$.rows}$;
  \item $\code{$B$.columns} \leq \code{$A$.columns}$.
  \end{itemize}
\end{fcode}


%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%

\SSTITLE{Vertical compose}

\begin{fcode}{void}{$A$.compose_v}{const base_matrix< T > & $B$, const base_matrix< T > & $C$}
  composes the matrices $B$ and $C$ to the matrix $A$, with $A = \begin{pmatrix} B \\ C
  \end{pmatrix}$, where the following conditions have to be satisfied:
  \begin{itemize}
  \item $\code{$B$.rows}, \code{$C$.rows} \leq \code{$A$.rows}$;
  \item $\code{$B$.columns}, \code{$C$.columns} \leq \code{$A$.columns}$.
  \end{itemize}
\end{fcode}

\begin{fcode}{void}{$A$.compose_v}{const T * $v$, const base_matrix< T > & $C$}
  composes the array $v$ and the matrix $C$ to the matrix $A$, with $A = \begin{pmatrix} v \\ C
  \end{pmatrix}$, where the following conditions have to be satisfied:
  \begin{itemize}
  \item $v \neq \code{NULL}$;
  \item $\code{$C$.rows} \leq \code{$A$.rows}$;
  \item $\code{$C$.columns} \leq \code{$A$.columns}$.
  \end{itemize}
  The behaviour of this function is undefined if $v$ has less than \code{$A$.columns} elements.
\end{fcode}

\begin{fcode}{void}{$A$.compose_v}{const base_vector< T > & $v$, const base_matrix< T > & $C$}
  composes the vector $v$ and the matrix $C$ to the matrix $A$, with $A = \begin{pmatrix} v \\ C
  \end{pmatrix}$, where the following conditions have to be satisfied:
  \begin{itemize}
  \item $\code{$v$.size} \leq \code{$A$.columns}$;
  \item $\code{$C$.rows} \leq \code{$A$.rows}$;
  \item $\code{$C$.columns} \leq \code{$A$.columns}$.
  \end{itemize}
\end{fcode}

\begin{fcode}{void}{$A$.compose_v}{const base_matrix< T > & $B$, const T * $v$}
  composes the matrix $B$ and the array $v$ to the matrix $A$, with $A = \begin{pmatrix} B \\ v
  \end{pmatrix}$, where the following conditions have to be satisfied:
  \begin{itemize}
  \item $v \neq \code{NULL}$;
  \item $\code{$B$.rows} \leq \code{$A$.rows}$;
  \item $\code{$B$.columns} \leq \code{$A$.columns}$.
  \end{itemize}
  The behaviour of this function is undefined if $v$ has less than \code{$A$.columns} elements.
\end{fcode}

\begin{fcode}{void}{$A$.compose_v}{const base_matrix< T > & $B$, const base_vector< T > & $v$}
  composes the matrix $B$ and the vector $v$ to the matrix $A$, with $A = \begin{pmatrix} B \\ v
  \end{pmatrix}$, where the following conditions have to be satisfied:
  \begin{itemize}
  \item $\code{$v$.size} \leq \code{$A$.columns}$;
  \item $\code{$B$.rows} \leq \code{$A$.rows}$;
  \item $\code{$B$.columns} \leq \code{$A$.columns}$.
  \end{itemize}
\end{fcode}


%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%

\STITLE{Swap Functions}

\begin{fcode}{void}{swap}{base_matrix< T > & $A$, base_matrix< T > & $B$}
  swaps $A$ and $B$.
\end{fcode}

\begin{fcode}{void}{$A$.swap_columns}{lidia_size_t $i$, lidia_size_t $j$}
  swaps the entries of the columns $i$ and $j$ in $A$.  If $0 \leq i,j < \code{$A$.columns}$
  doesn't hold, the \LEH will be invoked.
\end{fcode}

\begin{fcode}{void}{$A$.swap_rows}{lidia_size_t $i$, lidia_size_t $j$}
  swaps the entries of the rows $i$ and $j$ in $A$.  If $0 \leq i,j < \code{$A$.rows}$ doesn't
  hold, the \LEH will be invoked.
\end{fcode}


%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%

\STITLE{Diagonal Functions}

\begin{fcode}{void}{$A$.diag}{const T & $a$, const T & $b$}
  stores $a$ at all positions $(i,i)$ of matrix $A$ with $0 \leq i < \min(\code{$A$.rows},
  \code{$A$.columns})$ and $b$ at all other positions.
\end{fcode}

\begin{fcode}{void}{diag}{base_matrix< T > & $A$, const T & $a$, const T & $b$}
  stores $a$ at all positions $(i,i)$ of matrix $A$ with $0 \leq i < \min(\code{$A$.rows},
  \code{$A$.columns})$ and $b$ at all other positions.
\end{fcode}


%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%

\STITLE{Transpose Functions}

\begin{cfcode}{base_matrix< T >}{$A$.trans}{}
  returns $A^T$.
\end{cfcode}

\begin{fcode}{base_matrix< T >}{trans}{const base_matrix< T > & $A$}
  returns $A^T$.
\end{fcode}

\begin{fcode}{void}{$A$.trans}{const base_matrix< T > & $B$}
  stores $B^T$ to $A$.
\end{fcode}

\begin{fcode}{void}{trans}{base_matrix< T > & $A$, const base_matrix< T > & $B$}
  stores $B^T$ to $A$.
\end{fcode}


%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%

\IO

\label{base_matrix_io}
The \code{istream} operator \code{>>} and the \code{ostream} operator \code{<<} are overloaded.
The \code{istream} operator \code{>>} reads matrices in any of the supported formats from
istream.

The \code{ostream} operator \code{<<} outputs the matrix in the format given by the print mode
(see Access Functions, page \pageref{base_matrix_access}, for further information on how to set
the print mode).  By default, the ``\code{beautify mode}'' is used.  The following table shows,
which values of print mode correspond to the different output format.

\begin{center}
  \begin{tabular}{|c||c|}\hline
    \code{print_mode} & format \\\hline\hline
    0 & ``beautify''\\\hline
    1 & \LiDIA\\\hline
    2 & PARI \\\hline
    3 & MATHEMATICA \\\hline
    4 & MAPLE\\\hline
    5 & KANT \\\hline
  \end{tabular}
\end{center}
\begin{itemize}
\item By beautify format we mean the following ASCII format, which should be used only to output
  matrices on the screen, since it cannot be read by our library:
  \begin{displaymath}
    \begin{array}{cccccc}
      (& a_{0,0} & a_{0,1} & \dots & a_{0,c-1}&)\\
      (& a_{1,0} &  \dots & \dots & a_{1,c-1}&)\\
      (& \vdots & \vdots & \vdots & \vdots &)\\
      (& a_{r-1,0} & \dots &\dots & a_{r-1,c-1}&)
    \end{array}
  \end{displaymath}

\item By \LiDIA format we mean the following ASCII format:
  \begin{displaymath}
    r \sqcup c \sqcup a_{0,0} \sqcup a_{0,1} \sqcup
    \dots \sqcup a_{0,c-1} \sqcup a_{1,0} \sqcup \dots \sqcup a_{1,c-1}
    \sqcup  \dots \sqcup a_{r-1,0} \sqcup \dots \sqcup a_{r-1,c-1} \enspace,
  \end{displaymath}
  where $r = \code{$A$.rows}$ and $c = \code{$A$.columns}$.

\item By PARI format we mean the following ASCII format:
  \begin{displaymath}
    [a_{0,0}, a_{0,1}, \dots, a_{0,c-1}; a_{1,0}, \dots, a_{1,c-1};\
    \dots; a_{r-1,0}, \dots, a_{r-1,c-1}] \enspace,
  \end{displaymath}
  where $r = \code{$A$.rows}$ and $c = \code{$A$.columns}$.

\item By MATHEMATICA format we mean the following ASCII format:
  \begin{displaymath}
    \{\{a_{0,0}, a_{0,1},\dots, a_{0,c-1}\}, \{a_{1,0},\dots, a_{1,c-1}\},
    \dots, \{a_{r-1,0},\dots, a_{r-1,c-1}\}\} \enspace,
  \end{displaymath}
  where $r = \code{$A$.rows}$ and $c = \code{$A$.columns}$.
      
\item By MAPLE format we mean the following ASCII format:
  \begin{displaymath}
    \begin{array}{ccccc}
      array(1..r, 1..c,[&(1,1)=a_{0,0}, & (1,2)=a_{0,1}, & \dots, & (1,c)=a_{0,c-1},\\
      &(2,1)=a_{1,0}, &  \dots & \dots, &(2,c)=a_{1,c-1},\\
      &\vdots & \vdots & \vdots & \vdots\\
      &(r,1)=a_{r-1,0}, & \dots &\dots, &(r,c)=a_{r-1,c-1}]);
    \end{array}
  \end{displaymath}
  where $r = \code{$A$.rows}$ and $c = \code{$A$.columns}$.

\item By KANT format we mean the following ASCII format:
  \begin{displaymath}
    LIDIA:=Mat(Z,[[a_{0,0}, a_{0,1},\dots, a_{0,c-1}], [a_{1,0},\dots, a_{1,c-1}],
    \dots, [a_{r-1,0}, \dots, a_{r-1,c-1}]])
  \end{displaymath}
  where $r = \code{$A$.rows}$ and $c = \code{$A$.columns}$.
\end{itemize}


%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%

\STITLE{Interfaces}

The following member functions support writing to and reading from ASCII files in the standard
format of other computer algebra programs:

\begin{cfcode}{void}{$A$.write_to_stream}{ostream & out}
  writes matrix $A$ to ostream $out$ in \LiDIA format.
\end{cfcode}

\begin{fcode}{void}{$A$.read_from_stream}{istream & in}
  reads \LiDIA matrix $A$ from istream $in$.
\end{fcode}

\begin{cfcode}{void}{$A$.write_to_gp}{ostream & out}
  writes matrix $A$ to ostream $out$ in GP format.
\end{cfcode}

\begin{fcode}{void}{$A$.read_from_gp}{istream & in}
  reads GP matrix $A$ from istream.
\end{fcode}

\begin{cfcode}{void}{$A$.write_to_mathematica}{ostream & out}
  writes matrix $A$ to ostream $out$ in MATHEMATICA format.
\end{cfcode}

\begin{fcode}{void}{$A$.read_from_mathematica}{istream & in}
  reads MATHEMATICA matrix $A$ from istream.
\end{fcode}

\begin{cfcode}{void}{$A$.write_to_maple}{ostream & out}
  writes matrix $A$ to ostream $out$ in MAPLE format.
\end{cfcode}

\begin{fcode}{void}{$A$.read_from_maple}{istream & in}
  reads MAPLE matrix $A$ from istream.
\end{fcode}

\begin{cfcode}{void}{$A$.write_to_kash}{ostream & out}
  writes matrix $A$ to ostream $out$ in KASH format.
\end{cfcode}

\begin{fcode}{void}{$A$.read_from_kash}{istream & in}
  reads KASH matrix $A$ from istream.
\end{fcode}


%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%

\SEEALSO

\SEE{math_matrix}, \SEE{bigint_matrix},
\SEE{base_vector}, \SEE{math_vector}


%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%

\BUGS

By now, the function reading and writing matrices in GP-format don't understand the use of
`\bschar' as a multiple line break symbol.


%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%

\NOTES

\begin{enumerate}
\item As described in the template introduction (see page \pageref{template_introduction2}) for
  using an instance of type \code{base_matrix< T >} the type \code{T} has to have at least least
  have
  \begin{itemize}
  \item a swap-function \code{void swap(T &, T&)},
  \item the input-operator \code{>>},
  \item the output-operator \code{<<} and
  \item the assignment-operator \code{=}.
  \end{itemize}

\item As usually in C++ the numbering of columns and rows starts with zero.
\end{enumerate}


%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%

\EXAMPLES

\begin{quote}
\begin{verbatim}
#include <LiDIA/base_matrix.h>
#include <LiDIA/bigint.h>

int main()
{
    base_matrix < bigint > A(4,5);
    register int i, j;

    for (i = 0; i < A.get_no_of_rows(); i++)
        for (j = 0; j < A.get_no_of_columns(); j++)
            A.sto(i,j,(bigint)(i+j));
    cout << A << flush;

    return 0;
}
\end{verbatim}
\end{quote}

For further examples please refer to \path{LiDIA/src/templates/matrix/base_matrix_appl.cc}.


%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%

\AUTHOR

Stefan Neis, Patrick Theobald
