AbstractLinAlgPack: C++ Interfaces For Vectors, Matrices And Related Linear Algebra Objects Version of the Day
AbstractLinAlgPack_VectorSpaceSubSpace.cpp
00001 // @HEADER
00002 // ***********************************************************************
00003 // 
00004 // Moocho: Multi-functional Object-Oriented arCHitecture for Optimization
00005 //                  Copyright (2003) Sandia Corporation
00006 // 
00007 // Under terms of Contract DE-AC04-94AL85000, there is a non-exclusive
00008 // license for use of this work by or on behalf of the U.S. Government.
00009 // 
00010 // Redistribution and use in source and binary forms, with or without
00011 // modification, are permitted provided that the following conditions are
00012 // met:
00013 //
00014 // 1. Redistributions of source code must retain the above copyright
00015 // notice, this list of conditions and the following disclaimer.
00016 //
00017 // 2. Redistributions in binary form must reproduce the above copyright
00018 // notice, this list of conditions and the following disclaimer in the
00019 // documentation and/or other materials provided with the distribution.
00020 //
00021 // 3. Neither the name of the Corporation nor the names of the
00022 // contributors may be used to endorse or promote products derived from
00023 // this software without specific prior written permission.
00024 //
00025 // THIS SOFTWARE IS PROVIDED BY SANDIA CORPORATION "AS IS" AND ANY
00026 // EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
00027 // IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR
00028 // PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL SANDIA CORPORATION OR THE
00029 // CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL,
00030 // EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
00031 // PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR
00032 // PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF
00033 // LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING
00034 // NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
00035 // SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
00036 //
00037 // Questions? Contact Roscoe A. Bartlett (rabartl@sandia.gov) 
00038 // 
00039 // ***********************************************************************
00040 // @HEADER
00041 
00042 #include <assert.h>
00043 
00044 #include "AbstractLinAlgPack_VectorSpaceSubSpace.hpp"
00045 #include "AbstractLinAlgPack_VectorMutableSubView.hpp"
00046 #include "Teuchos_Assert.hpp"
00047 
00048 namespace AbstractLinAlgPack {
00049 
00050 VectorSpaceSubSpace::VectorSpaceSubSpace( const space_ptr_t& full_space, const Range1D& rng )
00051 {
00052   this->initialize(full_space,rng);
00053 }
00054 
00055 void VectorSpaceSubSpace::initialize( const space_ptr_t& full_space, const Range1D& rng )
00056 {
00057 #ifdef TEUCHOS_DEBUG
00058   TEUCHOS_TEST_FOR_EXCEPTION(
00059     full_space.get() == NULL, std::invalid_argument
00060     ,"VectorSpaceSubSpace::initialize(...): Error!" );
00061 #endif
00062   const index_type n = full_space->dim();
00063 #ifdef TEUCHOS_DEBUG
00064   TEUCHOS_TEST_FOR_EXCEPTION(
00065     !rng.full_range() && rng.ubound() > n, std::out_of_range
00066     ,"VectorSpaceSubSpace::initialize(...): Error, "
00067     "rng = [" << rng.lbound() << "," << rng.ubound() << "] is not in the range "
00068     "[1,vec->dim()] = [1," << n << "]" );
00069 #endif
00070   full_space_ = full_space;
00071   rng_ = rng.full_range() ? Range1D(1,n) : rng;
00072 }
00073 
00074 void VectorSpaceSubSpace::set_uninitialized()
00075 {
00076   full_space_ = Teuchos::null;
00077   rng_        = Range1D::Invalid;
00078 }
00079 
00080 #ifdef TEUCHOS_DEBUG
00081 void VectorSpaceSubSpace::validate_range(const Range1D& rng) const
00082 {
00083   const index_type n = this->dim();
00084   TEUCHOS_TEST_FOR_EXCEPTION(
00085     full_space_.get() == NULL, std::logic_error
00086     ,"VectorSpaceSubSpace::validate_range(rng): Error, Uninitialized" );
00087   TEUCHOS_TEST_FOR_EXCEPTION(
00088     full_space_.get() && !rng.full_range() && rng.ubound() > n, std::logic_error
00089     ,"VectorSpaceSubSpace::validate_range(rng): Error, "
00090     "rng = [" << rng.lbound() << "," << rng.ubound() << "] is not in the range "
00091     "[1,this->dim] = [1," << n << "]" );
00092 }
00093 #endif
00094 
00095 // Overridden from VectorSpace
00096 
00097 bool VectorSpaceSubSpace::is_compatible(const VectorSpace& another_space) const
00098 {
00099   if( this->dim() == another_space.dim() && this->is_in_core() && another_space.is_in_core() )
00100     return true;
00101   const VectorSpaceSubSpace
00102     *a_space = dynamic_cast<const VectorSpaceSubSpace*>(&another_space);
00103   if(!a_space)
00104     return false;
00105   return
00106     ( this->full_space_.get() == NULL && a_space->full_space_.get() == NULL )
00107     ||
00108     ( this->rng_ == a_space->rng_ && this->full_space_->is_compatible(*a_space->full_space_) );
00109 }
00110 
00111 bool VectorSpaceSubSpace::is_in_core() const
00112 {
00113   return full_space_->is_in_core();
00114 }
00115 
00116 index_type VectorSpaceSubSpace::dim() const
00117 {
00118   return full_space_.get() ? rng_.size() : 0;
00119 }
00120 
00121 VectorSpace::vec_mut_ptr_t VectorSpaceSubSpace::create_member() const
00122 {
00123   namespace rcp = MemMngPack;
00124   if( full_space_.get() )
00125     return Teuchos::rcp(
00126       new VectorMutableSubView(
00127         full_space_->create_member(), rng_ 
00128         ) );
00129   return Teuchos::null;
00130 }
00131 
00132 VectorSpace::space_ptr_t VectorSpaceSubSpace::clone() const
00133 {
00134   namespace rcp = MemMngPack;
00135   if( full_space_.get() )
00136     return Teuchos::rcp(new VectorSpaceSubSpace( full_space_->clone(), rng_ ));
00137   return Teuchos::rcp(new VectorSpaceSubSpace());
00138 }
00139 
00140 VectorSpace::space_ptr_t VectorSpaceSubSpace::sub_space(const Range1D& rng_in) const
00141 {
00142   namespace rcp = MemMngPack;
00143   if( full_space_.get() == NULL && rng_in == Range1D::Invalid )
00144     return Teuchos::rcp(this,false);
00145   validate_range(rng_in);
00146   const index_type dim         = this->dim();
00147   const Range1D    rng         = rng_in.full_range() ? Range1D(1,dim) : rng_in;
00148   if( rng.lbound() == 1 && rng.ubound() == dim )
00149     return space_ptr_t( this, false );
00150   const index_type this_offset = rng_.lbound() - 1;
00151   return Teuchos::rcp(
00152     new VectorSpaceSubSpace(
00153       full_space_
00154       ,Range1D( 
00155         this_offset  + rng.lbound()
00156         ,this_offset + rng.ubound() )
00157       ) );
00158 }
00159 
00160 } // end namespace AbstractLinAlgPack
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends