This file is indexed.

/usr/include/trilinos/AbstractLinAlgPack_MatrixExtractSparseElements.hpp is in libtrilinos-dev 10.4.0.dfsg-1ubuntu2.

This file is owned by root:root, with mode 0o644.

The actual contents of the file can be viewed below.

  1
  2
  3
  4
  5
  6
  7
  8
  9
 10
 11
 12
 13
 14
 15
 16
 17
 18
 19
 20
 21
 22
 23
 24
 25
 26
 27
 28
 29
 30
 31
 32
 33
 34
 35
 36
 37
 38
 39
 40
 41
 42
 43
 44
 45
 46
 47
 48
 49
 50
 51
 52
 53
 54
 55
 56
 57
 58
 59
 60
 61
 62
 63
 64
 65
 66
 67
 68
 69
 70
 71
 72
 73
 74
 75
 76
 77
 78
 79
 80
 81
 82
 83
 84
 85
 86
 87
 88
 89
 90
 91
 92
 93
 94
 95
 96
 97
 98
 99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
242
243
244
245
246
247
248
249
250
251
252
253
254
255
256
257
258
259
260
261
262
263
264
265
266
267
268
269
270
271
272
273
274
275
276
277
278
279
280
281
282
283
284
285
286
287
288
289
290
291
292
293
294
295
296
297
298
299
300
301
302
303
304
305
306
307
308
309
310
311
312
313
314
315
316
317
318
319
320
321
322
323
324
325
326
327
328
329
330
331
332
333
334
335
336
337
338
339
340
341
342
343
344
345
346
347
348
349
350
351
352
353
354
355
356
357
358
359
360
361
362
363
364
365
366
367
368
369
370
371
372
373
374
375
376
377
378
379
380
381
382
383
384
385
386
387
388
389
390
391
392
393
394
395
// @HEADER
// ***********************************************************************
// 
// Moocho: Multi-functional Object-Oriented arCHitecture for Optimization
//                  Copyright (2003) Sandia Corporation
// 
// Under terms of Contract DE-AC04-94AL85000, there is a non-exclusive
// license for use of this work by or on behalf of the U.S. Government.
// 
// This library is free software; you can redistribute it and/or modify
// it under the terms of the GNU Lesser General Public License as
// published by the Free Software Foundation; either version 2.1 of the
// License, or (at your option) any later version.
//  
// This library is distributed in the hope that it will be useful, but
// WITHOUT ANY WARRANTY; without even the implied warranty of
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
// Lesser General Public License for more details.
//  
// You should have received a copy of the GNU Lesser General Public
// License along with this library; if not, write to the Free Software
// Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307
// USA
// Questions? Contact Roscoe A. Bartlett (rabartl@sandia.gov) 
// 
// ***********************************************************************
// @HEADER

#ifndef ALAP_MATRIX_EXTRACT_SPARSE_ELEMENTS_H
#define ALAP_MATRIX_EXTRACT_SPARSE_ELEMENTS_H

#include "AbstractLinAlgPack_MatrixConvertToSparse.hpp"

namespace AbstractLinAlgPack {

/** \brief Interface for extracting nonzero elements from a banded subregion
 * of a permuted sparse matrix in one of several Fortran compatible formats.
 *
 * The formats supported are:
 *
 * Coordiante:
 \verbatim

     Aval[k], Arow[k], Acol[k], k = 0..num_nonzeros(...)-1
 \endverbatim
 * Compressed Row (Column):
 \verbatim

    Aval[k], Acol[k], k = 0..num_nonzeros(...)-1
    Arow_start[j], j = 0..rows()-1
 \endverbatim
 * This is meant to be the do-all interface for clients to use to extract nonzero elements
 * for sparse matrices.
 *
 * The idea is that given a matrix \a A, row and column permutations \c P and \c Q,
 * a range of rows and columns <tt>(rl,ru)</tt> and <tt>(cl,cu)</tt> defining a square submatrix
 * \a M and a range of lower and upper bands \c dl and \c du within the submatrix \a M, this
 * interface is used to extract those nonzero elements.
 *
 * In Matlab like terms we have:
 *
 * let <tt>M = (P'*A*Q)(rl:ru,cl:cu)</tt>
 *
 * This interface extracts nonzero elements from \a M within the banded region
 * <tt>[dl,du]</tt> where <tt>d = 0</tt> is the diagonal of \a M, <tt>d < 0</tt>
 * is below the diagonal and <tt>d > 0</tt> is above the diagonal.
 *
 * The following matrix is used in the documentation for the following
 * extraction functions.
 \verbatim

    [	1				6		9	]	1
    [			4				10	]	2
  A =	[			5					]	3
    [	2				7		11	]	4
    [	3				8		12	]	5

      1		2		3		 4

 \endverbatim
 *
 * Note that above, A has:<ul>
 * <li> <tt>A_nz == this->num_nonzeros(EXTRACT_FULL_MATRIX,ELEMENTS_FORCE_UNIQUE) == 12</tt>
 * <li> <tt>A_up_nz = this->num_nonzeros(EXTRACT_UPPER_TRIANGULAR,ELEMENTS_FORCE_UNIQUE) == 6</tt>
 * <li> <tt>A_lo_nz = this->num_nonzeros(EXTRACT_LOWER_TRIANGULAR,ELEMENTS_FORCE_UNIQUE) == 9</tt>
 * </ul>
 */
class MatrixExtractSparseElements
  : public virtual MatrixConvertToSparse
{
public:

  /** \brief Returns the number of nonzeros in the banded submatrix of the permuted matrix.
   *
   * Let \a B be the banded submatrix that is being specifed and let \a A be this
   * full matrix object.  Then the (dense) elemements of \a B are defined by:
   \verbatim

              / 0                                    : for dl <= (j-i) <= du
    B(i,j) =  |
              \ A(row_perm(i+rl-1),col_perm(j+cl-1)) : for (j-i) < dl || du < (j-i)

    for i = 1..ru-rl+1, j = 1..cu-cl+1
   \endverbatim
   * Above <tt>rl = row_rng.lbound()</tt>, ru = row_rng.ubound()</tt>,
   * <tt>cl = col_rng.lbound()</tt> and <tt>cu = col_rng.ubound()</tt>.
   *
   * Preconditions:<ul>
   *	<li> <tt>1 <= row_perm(i) <= this->rows(), i = 1..rows()</tt> (throw <tt>std::out_of_bounds</tt>)
   *	<li> <tt>1 <= col_perm(i) <= this->cols(), i = 1..cols()</tt> (throw <tt>std::out_of_bounds</tt>)
   *	<li> <tt>row_rng.ubound() <= this->rows()</tt> (throw <tt>std::out_of_bounds</tt>)
   *	<li> <tt>col_rng.ubound() <= this->cols()</tt> (throw <tt>std::out_of_bounds</tt>)
   *	<li> <tt>du >= dl</tt> (throw <tt>std::range_error</tt>)
   *	<li> <tt>-(ru-rl) <= dl && du <= (cu-cl)</tt> (throw <tt>std::out_of_bounds</tt>)
   *	</ul>
   *
   * To illustrate the behavior of this function consider the example matix \a A (see intro)
   * in the following example:
   *
   * Define the permutations as:
   \verbatim

   row_perm = { 2, 4, 1, 3, 5 }
   col_perm = { 3, 2, 1, 4 }
   \endverbatim
   * The permuted matrix <tt>(P'*A*Q)</tt> would then be:
   \verbatim

          2	|	1	[			4				10	]
          4	|	2	[	7				2		11	]
          1	|	3	[	6				1		9	]
    (P'*A*Q) =	3	|	4	[			5					]
          5	|	5	[	8				3		12	]

                  1		2		3		4
                  -		-		-		-
                  3		2		1		4
   \endverbatim
   * Now define the square submatrix in the range:
   \verbatim

   row_rng = [ rl, ru ] = [ 2, 5 ]
   col_rng = [ cl, cu ] = [ 2, 4 ]
   \endverbatim
   * The square submatrix is then:
   \verbatim

                4	|	1	[			2		11	]
    (P'*A*Q)(r1:r2,cl:cu) =	1	|	2	[			1		9	]
                3	|	3	[	5					]

                        1		2		3
                        -		-		-
                        2		1		4
   \endverbatim
   * Now define the range of diagonals as:
   \verbatim

   dl = -1, du = 1
   \endverbatim
   * This finally gives us our matrix that we wish to extract nonzeros
   * from as (the x's show elemements that where excluded out of the 
   * diagonal range:
   \verbatim

      4	|	1	[			4		x	]
    B =	1	|	2	[			1		9	]
      3	|	3	[	x					]

              1		2		3
              -		-		-
              2		1		4
   \endverbatim
   * Now we can see that for this example that this->count_nonzeros() would
   * return 3.
   *
   * In summary, for the example A shown above we have:
   *
   * Input:
   \verbatim
        element_uniqueness = ELEMENTS_FORCE_UNIQUE
    row_perm[]         = { 2, 4, 1, 3, 5 }
    col_perm[]         = { 3, 2, 1, 4 }
    row_rng            = [ 2, 5 ]
    col_rng            = [ 2, 4 ]
    dl                 = -1
    du                 = +1
   \endverbatim
   * Output:
   \verbatim

    3 <- count_nonzeros(element_uniqueness,row_perm,col_perm,row_rng,col_rng,dl,du)
   \endverbatim
   *
   * @param  element_uniqueness
   *              [in] Determines if element row and column indexes must be unique.<ul>
   *              <li> \c ELEMENTS_FORCE_UNIQUE: The row and column indexes must be unique.
   *              <li> \c ELEMENTS_ALLOW_DUPLICATES_SUM: Entries with duplicate row and
   *                   column indexes are allowed with the understanding that the values
   *                   will be summed.
   *              </ul>
   * @param  inv_row_perm
   *              [in] Arary (length \c this->rows()) Defines the row permutation \c P.
   *              Row \c i of \c A is row \c inv_row_perm[i-1] of \c <tt>(P'*A)</tt> .
   *              If <tt>inv_row_perm==NULL</tt> on input then the identity permutation
   *              <tt>P = I</tt> is used.
   * @param  inv_col_perm
   *              [in] Arary (length \c this->cols()) Defines the column permutation \c Q.
   *              Column \c j of \c A is column \c inv_col_perm[j-1] of <tt>(A*Q)</tt>.
   *              If <tt>inv_col_perm==NULL</tt> on input then the identity permutation
   *              <tt>Q = I</tt> is used.
   * @param  row_rng
   *              [in] Defines the range of rows <tt>[rl,ru]</tt> that the submatrix
   *              of <tt>(P'*A*Q)</tt> is taken from (see preconditions).
   * @param  col_rng
   *              [in] Defines the range of columns <tt>[cl,cu]</tt> that the submatrix
   *              of </tt>(P'*A*Q)</tt> is taken from (see preconditions).
   * @param  dl   [in] Lower diagonal to extract elements above (see preconditions).
   * @param  du   [in] Upper diagonal to extract elements below (see preconditions).
   */
  virtual index_type count_nonzeros(
    EElementUniqueness    element_uniqueness
    ,const index_type     inv_row_perm[]
    ,const index_type     inv_col_perm[]
    ,const Range1D        &row_rng
    ,const Range1D        &col_rng
    ,index_type           dl
    ,index_type           du
    ) const = 0;

  /** \brief Extract elements in a coordinate data structure.
   *
   * Let B be the scaled banded submatrix that is being specifed
   * and let A be this matrix object.  Then the elemements
   * of B are defined by:
   \verbatim

              / 0                                          : for dl <= (j-i) <= du
    B(i,j) =  |
              \ alpha*A(row_perm(i+rl-1),col_perm(j+cl-1)) : for (j-i) < dl || du < (j-i)

    for i = 1..ru-rl+1, j = 1..cu-cl+1
   \endverbatim
   * were <tt>rl = row_rng.lbound()</tt>, <tt>ru = row_rng.ubound()</tt>,
   * <tt>cl = col_rng.lbound()</tt> and <tt>cu = col_rng.ubound()</tt>.
   *
   * The client can extract the structure in \c Arow[] and \c Acol[] and/or
   * the nonzero elements in \c Aval[].  If the client wants to extract
   * the structure it sets
   * <tt>len_Aij = this->count_nonzeros()</tt>
   * and then \c Arow[] and \c Acol[] are filled with the row and column indexes.
   * If the client wants the nonzero values it sets
   * <tt>len_Aval = this->count_nonzeros()</tt>
   * and then \c Aval[] will be set on output.
   *
   * The input arguments passed to <tt>this->count_nonzeros()</tt> must correspond to the
   * same arguments passed to this function.
   *
   * To illustrate the behavior of this function consider the same example as
   * outlined in the documentation for \c count_nonzeros().  Let's assume
   * that we want to scale the example banded matrix by <tt>alpha = 2.0</tt>,
   * make the row and column indexes start at (4,7) and extract the
   * structure (<tt>len_Aij > 0</tt>) and the nonzero values (<tt>len_Aval</tt>).
   * The input and output from this function for this example would then be:
   *
   * Input:
   \verbatim
        elements_uniqueness = ELEMENTS_FORCE_UNIQUE
    row_perm            = { 2, 4, 1, 3, 5 }
    col_perm            = { 3, 2, 1, 4 }
    row_rng             = [ 2, 5 ]
    col_rng             = [ 2, 4 ]
    dl                  = -1
    du                  = +1
    alpha               = 2.0
    len_Aval            = count_nonzeros(...) = 3
    len_Aij             = count_nonzeros(...) = 3
    row_offset          = 3
    col_offset          = 6 
   \endverbatim
   * Output:
   \verbatim

    k  A(i,j)  B(i,j)  Avar  Arow  Acol
    -  ------  ------  ----  ----  ----
    1  4(4,1)  4(1,2)     8     4     8
    2  1(1,1)  1(2,2)     2     5     8
    3  9(1,5)  9(2,3)    18     5     9
   \endverbatim
   * Some of the most common uses of this interface are:<ul>
   * <li> Extract rectuangular submatrices: <tt>(bl = -(ru-rl+1) && bu = (cu-cl+1))</tt>
   * <li> Extract upper triangular region:  <tt>(bl = 0 && bu = (cu-cl+1))</tt>
   * <li> Extract lower triangular region:  <tt>(bl = -(ru-rl+1) && bu = 0)</tt>
   * </ul>
   *
   * @param  element_uniqueness
   *                  [in] Same as passed to \c count_nonzeros(...).
   * @param  row_perm [in] Same as passed to \c count_nonzeros(...).
   * @param  col_perm [in] Same as passed to \c count_nonzeros(...).
   * @param  row_rng  [in] Same as passed to \c count_nonzeros(...).
   * @param  col_rng  [in] Same as passed to \c count_nonzeros(...).
   * @param  dl       [in] Same as passed to \c count_nonzeros(...).
   * @param  du       [in] Same as passed to \c count_nonzeros(...).
   * @param  alpha    [in] Scaling parameter (see above)
   * @param  len_Aval [in] If the client wants to extract the nonzero values
   *                  of the matrix in \c Aval[] then this should be set to
   *                  <tt>len_Aval = this->count_nonzeros(...)</tt>.
   *                  Otherwise \c len_Avar should be set to zero.
   * @param  Aval     [out] If <tt>len_Aval > 0</tt> then \c Aval must point to
   *                  the begining of an array of length \c len_Aval.
   *                  If <tt>len_Aval == 0</tt> then \c Aval may be NULL.
   *                  On output, \c Aval[k] is the nonzero value of the kth
   *                  nonzero element, for <tt>k = 0...len_Aval-1</tt>.
   * @param  len_Aij  [in] If the client wants to extract the structure
   *                  of the matrix in \c Arow[] and \c Acol[] then this
   *                  should be set to <tt>len_Aij = this->num_nonzeros(...)</tt>.
   *                  Otherwise \c len_Aij should be set to zero.
   * @param  Arow     [out] If <tt>len_Aij > 0</tt> then \c Arow must point to
   *                  the begining of an array of length \c len_Aij.
   *                  If <tt>len_Aij == 0</tt> then Arow must be \c NULL.
   *                  On output, \c Arow[k] is the row index of the kth
   *                  nonzero element, for <tt>k = 0...len_Aij-1</tt>.
   * @param  Acol     [out] If <tt>len_Aij > 0</tt> then \c Acol must point
   *                  to the begining of an array of length \c len_Aij.
   *                  If <tt>len_Aij == 0</tt> then \c Acol must be \c NULL.
   *                  On output, \c Acol[k] is the column index of the kth
   *                  nonzero element, for <tt>k = 0...len_Aij-1</tt>.
   * @param  row_offset
   *                  [in] The row indexes in \c Arow[] are offset by
   *                  <tt>+row_offset</tt> on output.  To leave the first
   *                  row index as 1 set <tt>row_offset = 0</tt>.  This is to
   *                  allow the client to place this matrix as a submatrix
   *                  into a larger matrix stored in the coordinate format.
   *                  Default value = 0.	  
   * @param  col_offset
   *                  [in] The column indexes in \c Acol[] are offset by
   *                  <tt>+col_offset</tt> on output.  To leave the first
   *                  column index as 1 set <tt>col_offset = 0</tt>.  This is to
   *                  allow the client to place this matrix as a submatrix
   *                  into a larger matrix stored in the coordinate format.
   *                  Default value = 0.	  
   */
  virtual void coor_extract_nonzeros(
    EElementUniqueness    element_uniqueness
    ,const index_type     inv_row_perm[]
    ,const index_type     inv_col_perm[]
    ,const Range1D        &row_rng
    ,const Range1D        &col_rng
    ,index_type           dl
    ,index_type           du
    ,value_type           alpha
    ,const index_type     len_Aval
    ,value_type           Aval[]
    ,const index_type     len_Aij
    ,index_type           Arow[]
    ,index_type           Acol[]
    ,const index_type     row_offset = 0
    ,const index_type     col_offset = 0
    ) const = 0;

  // ToDo: Add methods for extracting compressed row (column) elements!

  /** @name Overridden from MatrixConvertToSparse */
  //@{

  /** \brief . */
  index_type num_nonzeros(
    EExtractRegion        extract_region
    ,EElementUniqueness   element_uniqueness
    ) const;
  /** \brief . */
  void coor_extract_nonzeros(
    EExtractRegion                extract_region
    ,EElementUniqueness           element_uniqueness
    ,const index_type             len_Aval
    ,value_type                   Aval[]
    ,const index_type             len_Aij
    ,index_type                   Arow[]
    ,index_type                   Acol[]
    ,const index_type             row_offset
    ,const index_type             col_offset
    ) const;

  //@}

private:

  /** \brief . */
  void get_dl_du( EExtractRegion extract_region, index_type* dl, index_type* du ) const;

};	// end class MatrixExtractSparseElements

}	// end namespace AbstractLinAlgPack 

#endif	// ALAP_MATRIX_EXTRACT_SPARSE_ELEMENTS_H