|
EpetraExt Development
|
00001 // @HEADER 00002 // *********************************************************************** 00003 // 00004 // EpetraExt: Epetra Extended - Linear Algebra Services Package 00005 // Copyright (2001) 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 // This library is free software; you can redistribute it and/or modify 00011 // it under the terms of the GNU Lesser General Public License as 00012 // published by the Free Software Foundation; either version 2.1 of the 00013 // License, or (at your option) any later version. 00014 // 00015 // This library is distributed in the hope that it will be useful, but 00016 // WITHOUT ANY WARRANTY; without even the implied warranty of 00017 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 00018 // Lesser General Public License for more details. 00019 // 00020 // You should have received a copy of the GNU Lesser General Public 00021 // License along with this library; if not, write to the Free Software 00022 // Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 00023 // USA 00024 // Questions? Contact Michael A. Heroux (maherou@sandia.gov) 00025 // 00026 // *********************************************************************** 00027 // @HEADER 00028 00029 #include <EpetraExt_SolverMap_CrsMatrix.h> 00030 00031 #include <Epetra_CrsGraph.h> 00032 #include <Epetra_CrsMatrix.h> 00033 #include <Epetra_Map.h> 00034 #include <Epetra_Comm.h> 00035 00036 #include <vector> 00037 00038 namespace EpetraExt { 00039 00040 CrsMatrix_SolverMap:: 00041 ~CrsMatrix_SolverMap() 00042 { 00043 if( newObj_ && newObj_ != origObj_ ) delete newObj_; 00044 if( NewGraph_ ) delete NewGraph_; 00045 if( NewColMap_ ) delete NewColMap_; 00046 } 00047 00048 CrsMatrix_SolverMap::NewTypeRef 00049 CrsMatrix_SolverMap:: 00050 operator()( OriginalTypeRef orig ) 00051 { 00052 origObj_ = &orig; 00053 00054 assert( !orig.IndicesAreGlobal() ); 00055 00056 //test if matrix has missing local columns in its col std::map 00057 const Epetra_Map & RowMap = orig.RowMap(); 00058 const Epetra_Map & DomainMap = orig.DomainMap(); 00059 const Epetra_Map & ColMap = orig.ColMap(); 00060 const Epetra_Comm & Comm = RowMap.Comm(); 00061 int NumMyRows = RowMap.NumMyElements(); 00062 int NumCols = DomainMap.NumMyElements(); 00063 int Match = 0; 00064 for( int i = 0; i < NumCols; ++i ) 00065 if( DomainMap.GID(i) != ColMap.GID(i) ) 00066 { 00067 Match = 1; 00068 break; 00069 } 00070 00071 int MatchAll = 0; 00072 Comm.SumAll( &Match, &MatchAll, 1 ); 00073 00074 if( !MatchAll ) 00075 { 00076 newObj_ = origObj_; 00077 } 00078 else 00079 { 00080 //create ColMap with all local rows included 00081 std::vector<int> Cols(NumCols); 00082 //fill Cols list with GIDs of all local columns 00083 for( int i = 0; i < NumCols; ++i ) 00084 Cols[i] = DomainMap.GID(i); 00085 00086 //now append to Cols any ghost column entries 00087 int NumMyCols = ColMap.NumMyElements(); 00088 for( int i = 0; i < NumMyCols; ++i ) 00089 if( !DomainMap.MyGID( ColMap.GID(i) ) ) Cols.push_back( ColMap.GID(i) ); 00090 00091 int NewNumMyCols = Cols.size(); 00092 int NewNumGlobalCols; 00093 Comm.SumAll( &NewNumMyCols, &NewNumGlobalCols, 1 ); 00094 //create new column std::map 00095 NewColMap_ = new Epetra_Map( NewNumGlobalCols, NewNumMyCols,&Cols[0], DomainMap.IndexBase(), Comm ); 00096 00097 //New Graph 00098 std::vector<int> NumIndicesPerRow( NumMyRows ); 00099 for( int i = 0; i < NumMyRows; ++i ) 00100 NumIndicesPerRow[i] = orig.NumMyEntries(i); 00101 NewGraph_ = new Epetra_CrsGraph( Copy, RowMap, *NewColMap_, &NumIndicesPerRow[0] ); 00102 00103 int MaxNumEntries = orig.MaxNumEntries(); 00104 int NumEntries; 00105 std::vector<int> Indices( MaxNumEntries ); 00106 for( int i = 0; i < NumMyRows; ++i ) 00107 { 00108 int RowGID = RowMap.GID(i); 00109 orig.Graph().ExtractGlobalRowCopy( RowGID, MaxNumEntries, NumEntries, &Indices[0] ); 00110 NewGraph_->InsertGlobalIndices( RowGID, NumEntries, &Indices[0] ); 00111 } 00112 const Epetra_Map & RangeMap = orig.RangeMap(); 00113 NewGraph_->FillComplete(DomainMap,RangeMap); 00114 00115 //intial construction of matrix 00116 Epetra_CrsMatrix * NewMatrix = new Epetra_CrsMatrix( View, *NewGraph_ ); 00117 00118 //insert views of row values 00119 int * myIndices; 00120 double * myValues; 00121 int indicesCnt; 00122 int numMyRows = NewMatrix->NumMyRows(); 00123 for( int i = 0; i < numMyRows; ++i ) 00124 { 00125 orig.ExtractMyRowView( i, indicesCnt, myValues, myIndices ); 00126 NewGraph_->ExtractMyRowView( i, indicesCnt, myIndices ); 00127 00128 NewMatrix->InsertMyValues( i, indicesCnt, myValues, myIndices ); 00129 } 00130 00131 NewMatrix->FillComplete(DomainMap,RangeMap); 00132 00133 newObj_ = NewMatrix; 00134 } 00135 00136 return *newObj_; 00137 } 00138 00139 } // namespace EpetraExt 00140
1.7.4