/usr/include/trilinos/AbstractLinAlgPack_VectorSpace.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 396 397 398 399 400 401 | // @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_VECTOR_SPACE_HPP
#define ALAP_VECTOR_SPACE_HPP
#include "AbstractLinAlgPack_InnerProduct.hpp"
#include "Teuchos_AbstractFactory.hpp"
namespace AbstractLinAlgPack {
/** \brief Abstract interface for objects that represent a space for mutable coordinate vectors.
*
* This interface acts primarily as an "Abstract Factory" interface for creating \c VectorMutable
* objects using the \c create_member() method. A <tt>%VectorSpace</tt> object may also be able
* to create \c MultiVectorMutable objects which represent a compact collection of vectors.
* Every application area should be able to define a <tt>%MultiVectorMutable</tt> subclass if
* it can define a <tt>%VectorMutable</tt> subclass.
* A secondary role for <tt>%VectorSpace</tt> objects is to test for compatibility of vector spaces
* (and the vectors and matrix using those spaces) objects using the \c is_compatible() method.
*
* Given a <tt>%VectorSpace</tt> object it may also be possible to create sub-spaces using the
* \c sub_space() method. This subspace is not a sub-space in the mathematical sense but instead
* referese to a sub-range of vector elements.
*
* Any <tt>%VectorSpace</tt> object can be copied using the \c clone() method. Therefore,
* clients have complete control over the lifetime of <tt>%VectorSpace</tt> objects.
*
* A <tt>%VectorSpace</tt> object can exist independent from any individual <tt>VectorMutable</tt>
* (or \c MutiVectorMutable) object; Or, a <tt>%VectorSpace</tt> object can have a lifetime that is
* dependent on a single <tt>Vector</tt> ( or \c MultiVector) object. The same interface can
* serve both roles.
*
* Note that a <tt>%VectorSpace</tt> object can create <tt>MultiVectorMutable</tt> objects
* with any number of column vectors, and <tt>MultiVector::space_rows()</tt> gives a vector space
* of the dimension. Therefore, the creation of a multi-vector provides a way for clients to create
* vector spaces of any arbitrary (although small usually) dimension. In order to give the client
* the same ability without having to create a multi-vector, the method <tt>small_vec_spc_fcty()</tt>
* returns a <tt>VectorSpaceFactory</tt> object that can create vector spaces of small dimension.
* These created vector spaces can be used by the created <tt>MultiVectorMutable</tt> objects
* (see <tt>create_members()</tt>). These vector spaces are also used for the default implementation
* of <tt>space(P,P_trans)</tt> (see below). Since a <tt>%VectorSpace</tt> object is not required
* to create <tt>MultiVectorMutable</tt> objects using <tt>create_members()</tt> a <tt>%VectorSpace</tt>
* object is also not required to return a <tt>VectorSpaceFactory</tt> object from <tt>small_vec_spc_fcty()</tt>.
* to be consistent.
*
* A vector space is also where the inner product for the space is
* defined. It is anticipated that the same implementation of vectors
* and vector spaces will be reused over and over again with different
* definitions of the inner product. Therefore, the inner product is
* represented as a seperate strategy object. For example, the same
* parallel vector implementation can be used with several different
* inner product definitions. In some cases, the same inner product
* stategy object may be able to be used with diffeent vector implemenations
* (such as the dot product for example).
*
* Note that the default copy constructor will transfer the inner product object correctly
* but the subclass must make sure to copy the inner product object in \c clone() operation.
* This is little price to pay considering what this design takes care of already for
* <tt>%VectorSpace</tt> subclasses.
* However, the default copy constructor will only make a shallow copy of the inner product
* object but since this object may never be changed, this is perhaps the correct behavior.
* For any other behavior and the subbclass will have to take care of it.
*
* A vector space may also have another advanced feature; it may be able to define other
* vector spaces based on a gather operation of selected vector elements given a
* <tt>GenPermMatrixSlice</tt> (<tt>GPMS</tt>) object. For example, suppose that a
* <tt>GPMS</tt> object \c P is defined which extracts a (relatively) small number of elements
* of a vector \c v (from the vector space \c *this) and gathers them into a small vector \c q.
\verbatim
q = op(P)*v
\endverbatim
* The question is, to what vector space \c Q does the vector \c q belong?
* The answer is returned by the method <tt>Q = this->space(P,P_trans)</tt>.
* Theoretically, \c op(P) could be any <tt>GPMS</tt> object and
* <tt>this->space(P,P_trans)</tt> should always be able
* to return a non-NULL vector space object. In reality, the client should only
* expect <tt>this->space(P,P_trans).get() != NULL</tt> if
* <tt>q_dim = BLAS_Cpp::rows( P.rows(), P.cols(), P_trans )</tt> is a relatively
* small number (i.e. less than a few thousand). If \c q_dim is small, then the vector
* \c q can always be represented as a local serial vector. This is not a terribly
* difficult requirement and any <tt>%VectorSpace</tt> subclass should be able to
* comply.
*
* The returned vector space \c Q must have the property that the scatter operation is
* also defined. In other words, it must be that:
\verbatim
this->space(P,P_trans)->space(P,trans_not(P_trans))->is_compatible(*this) == true
\endverbatim
* This property insures that the gather and scatter operations can be implemented
* properly.
*/
class VectorSpace
: public Teuchos::AbstractFactory<VectorMutable>
{
public:
/// Thrown if vector spaces are incompatible
class IncompatibleVectorSpaces : public std::logic_error
{public: IncompatibleVectorSpaces(const std::string& what_arg) : std::logic_error(what_arg) {}};
/** \brief . */
typedef Teuchos::RCP<const InnerProduct> inner_prod_ptr_t;
/** \brief . */
typedef Teuchos::RCP<const VectorSpace> space_ptr_t;
/** \brief . */
typedef Teuchos::RCP<const VectorSpaceFactory> space_fcty_ptr_t;
/** \brief . */
typedef Teuchos::RCP<VectorMutable> vec_mut_ptr_t;
/** \brief . */
typedef Teuchos::RCP<MultiVectorMutable> multi_vec_mut_ptr_t;
/** @name Constructors / initializers */
//@{
/// Calls \c inner_prod()
VectorSpace( const inner_prod_ptr_t& inner_prod = Teuchos::null );
/** \brief Initialize with an inner product object.
*
* @param inner_prod [in] Smart pointer to inner product strategy object.
* If <tt>inner_prod.get()==NULL</tt> then an
* \c InnerProductDot object will be used instead.
*
* Postconditions:<ul>
* <li> [<tt>inner_prod.get() != NULL</tt>] <tt>this->inner_prod().get() == inner_prod.get()</tt>
* <li> [<tt>inner_prod.get() == NULL</tt>] <tt>dynamic_cast<InnerProductDot*>(this->inner_prod().get()) != NULL</tt>
* </ul>
*/
virtual void inner_prod( const inner_prod_ptr_t& inner_prod );
/** \brief Return the smart pointer to the inner product strategy object.
*
* Postconditions:<ul>
* <li> <tt>return.get() != NULL</tt>
* </ul>
*/
virtual const inner_prod_ptr_t inner_prod() const;
//@}
/** @name Pure virtual functions that must be overridden */
//@{
/** \brief Create a clone of \c this vector space object.
*
* The returned vector space object is expected to be independent from \c this
* and have a lifetime that extends beyond \c this. This makes a vector space
* class a little hander to implement by makes for much better flexibility
* for the client. A complete implementation of <tt>%VectorSpace</tt> is not
* allowed to return \c NULL from this method.
*
* Postconditions:<ul>
* <li> <tt>return.get() != NULL</tt>
* </ul>
*/
virtual space_ptr_t clone() const = 0;
/** \brief Compare the compatibility of two vector spaces.
*
* If this function returns true, then vectors created from
* either of the vector spaces will be compatible and can
* be combined in vector operations.
*
* Invariants:<ul>
* <li> [<tt>this->is_compatible(vec_spc) == true</tt>] <tt>vec_spc.is_compatible(*this) == true</tt>
* </ul>
*
* Postconditions:<ul>
* <li> [<tt>this->dim() != vec_spc.dim()</tt>] <tt>return == false</tt>
* </ul>
*/
virtual bool is_compatible(const VectorSpace& vec_spc ) const = 0;
/** \brief Return the dimmension of the vector space.
*/
virtual index_type dim() const = 0;
/** \brief Create a vector member from the vector space.
*
* Postconditions:<ul>
* <li> <tt>return.get() != NULL</tt>
* <li> <tt>return->dim() == this->dim()</tt>
* <li> <tt>return->space().is_compatible(*this) == true</tt>
* </ul>
*
* @return Returns a smart reference counted pointer to a dynamically
* allocated vector object. After construction the values returnd by
* <tt>return->get_ele(i)</tt> are unspecified (uninitialized). This allows for
* faster execution times. Note that <tt>&return->space()</tt> does not have to
* be equal to <tt>this</tt>.
*/
virtual vec_mut_ptr_t create_member() const = 0;
//@}
/** @name Virtual functions with default implementations */
//@{
/** \brief Returns true if the vectors are in core.
*
* If this function returns true then it means that the vector
* access functions <tt>Vector::get_sub_vector()</tt> and
* <tt>VectorMutable::get_sub_vector()</tt> can be safely called and
* can be expected to be fairly efficient. If this function does
* return true then the functions <tt>Vector::get_sub_vector()</tt>,
* <tt>Vector::free_sub_vector()</tt>,
* <tt>VectorMutable::get_sub_vector()</tt> and
* <tt>VectorMutable::commit_sub_vector()</tt> had better be
* overridden and had better not call
* <tt>Vector::apply_op(...)</tt>.
*
* The default implementation returns <tt>false</tt>
*/
virtual bool is_in_core() const;
/** \brief Return a <tt>VectorSpaceFactory</tt> object for the creation of
* vector spaces with a small dimension.
*
* ToDo: Finish documentation!
*
* The default implementation returns <tt>return.get() == NULL</tt>.
*
*/
virtual space_fcty_ptr_t small_vec_spc_fcty() const;
/** \brief Create a vector member from the vector space initialized to a scalar.
*
* @param alpha [in] Scalar that all elements of allocated vector are
* initialized to.
*
* Postconditions:<ul>
* <li> <tt>return.get() != NULL</tt>
* <li> <tt>return->dim() == this->dim()</tt>
* <li> <tt>return->space().is_compatible(*this) == true</tt>
* </ul>
*
* @return Returns a smart reference counted pointer to a dynamically
* allocated vector object. After construction the values returnd by
* <tt>return->get_ele(i)</tt> are equal to <tt>alpha</tt>.
* Note that <tt>&return->space()</tt> does not have to
* be equal to <tt>this</tt>.
*
* The default implementation just calls \c create_member() and then
* assigns <tt>alpha</tt> before returning the smart pointer object.
*/
virtual vec_mut_ptr_t create_member(const value_type& alpha) const;
/** \brief Create a set of vector members (a \c MultiVectorMutable) from the vector space.
*
* Preconditions:<ul>
* <li> <tt>num_vecs >= 1</tt> (throw <tt>???</tt>)
* </ul>
*
* Postconditions:<ul>
* <li> [<tt>return.get() != NULL</tt>] <tt>return->space_cols().is_compatible(*this) == true</tt>
* <li> [<tt>return.get() != NULL</tt>] <tt>return->space_rows().dim() == num_vecs</tt>
* <li> [<tt>return.get() != NULL</tt>] <tt>(return->access_by() & MultiVector::COL_ACCESS) == true</tt>
* </ul>
*
* @return Returns a smart reference counted pointer to a dynamically
* allocated multi-vector object. After construction the values returnd by
* <tt>return->col(j)->get_ele(i)</tt> are unspecified (uninitialized). This
* allows for faster execution times. Note that <tt>&return->space_cols()</tt>
* does not have to be equal to <tt>this</tt>. It is allowed for a vector
* space implementation to refuse to create multi-vectors and can return
* \c NULL from this method.
*
* The default implementation just returns \c NULL.
*/
virtual multi_vec_mut_ptr_t create_members(size_type num_vecs) const;
//@}
/** \brief Create a transient sub-space of the current vector space.
*
* @param rng [in] The range of the elements to extract a vector sub-space.
*
* Preconditions:<ul>
* <li> <tt>rng.ubound() <= this->dim()</tt> (<tt>throw std::out_of_range</tt>)
* </ul>
*
* Postconditions:<ul>
* <li> [<tt>return.get() != NULL</tt>] <tt>return->dim() == rng->size()</tt>
* </ul>
*
* @return Returns a smart reference counted pointer to a dynamically
* allocated vector space object. Note that the vector object returned
* by <tt>this->sub_space(rng).create_member()</tt> should be exactly equivalent
* to the vector returned by
* <tt>this->create_member()->sub_view(rng)->space()->create_member()</tt>.
* It is allowed for the implementation to return <tt>return->get() == NULL</tt>
* for arbitrary values of <tt>rng</tt>. Only some <tt>rng</tt> ranges may be allowed
* but they will be appropriate for the application at hand. However, a
* very good implementation should be able to accomidate any valid <tt>rng</tt>
* that meets the basic preconditions.
*
* Note that if two vector space objects <tt>X</tt> and <tt>Y</tt> are compatible
* (i.e. <tt>X.is_compatible(Y) == true</tt>, then it is also expected that
* <tt>X.sub_space(rng)->is_compatible(*Y.sub_space(rng))</tt> will also be \c true.
* However, in general it can not be expected that
* <tt>X.sub_space(rng1)->is_compatible(*X.sub_space(rng2)) == true</tt>, even if
* <tt>rng1.size() == rng2.size()</tt>. For serial vectors, it may
* be but for parallel vectors it will most certainly not be. Therefore, in
* general, don't assume that arbitrary subsets of the vector spaces will be
* compatible, even if the sizes of these subspaces are the same.
*
* The default implementation uses the subclass \c VectorSpaceSubSpace to
* represent any arbitrary sub-space but this can be very inefficient if the
* sub-space is very small compared this this full vector space.
*/
virtual space_ptr_t sub_space(const Range1D& rng) const;
/// Inlined to call <tt>this->sub_space(Range1D(il,iu))</tt>.
space_ptr_t sub_space( const index_type il, const index_type iu ) const;
/** \brief Create a vector space for vector to gather the elements into.
*
* @param P [in] A <tt>GenPermMatrixSlice</tt> object specifying the map.
* @param P_trans [in] Determines if <tt>P</tt> is transposed or not.
*
* Preconditions:<ul>
* <li> ???
* </ul>
*
* Postconditions:<ul>
* <li> [<tt>return.get()!=NULL</tt>]
* return->space(P,trans_not(P_trans))->is_compatible(*this) == true
* </ul>
*
* @return Returns a smart reference counted pointer to a dynamically
* allocated vector space object.
*
* ToDo: Finish documentation!
*
* The default implementation returns <tt>return.get() == NULL</tt>.
*/
virtual space_ptr_t space(
const GenPermMatrixSlice &P
,BLAS_Cpp::Transp P_trans
) const;
//@}
/** @name Overridden from AbstractFactory */
//@{
/// Just calls <tt>this->create_member()</tt> by default!
obj_ptr_t create() const;
//@}
private:
#ifdef DOXYGEN_COMPILE
const InnerProduct *inner_prod;
#else
inner_prod_ptr_t inner_prod_;
#endif
}; // end class VectorSpace
// ////////////////////////////////////////////////
// Inline members
inline
VectorSpace::space_ptr_t
VectorSpace::sub_space( const index_type il, const index_type iu ) const
{
return this->sub_space(Range1D(il,iu));
}
} // end namespace AbstractLinAlgPack
#endif // ALAP_VECTOR_SPACE_HPP
|