00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029 #ifndef THYRA_SPMD_MULTI_VECTOR_SERIALIZER_HPP
00030 #define THYRA_SPMD_MULTI_VECTOR_SERIALIZER_HPP
00031
00032 #include "Thyra_SpmdMultiVectorSerializerDecl.hpp"
00033 #include "Thyra_SpmdVectorSpaceDefaultBase.hpp"
00034 #include "Thyra_MultiVectorBase.hpp"
00035 #include "Thyra_DetachedMultiVectorView.hpp"
00036
00037 namespace Thyra {
00038
00039 template<class Scalar>
00040 SpmdMultiVectorSerializer<Scalar>::SpmdMultiVectorSerializer(
00041 const bool binaryMode
00042 )
00043 :binaryMode_(binaryMode)
00044 {}
00045
00046 template<class Scalar>
00047 bool SpmdMultiVectorSerializer<Scalar>::isCompatible(
00048 const MultiVectorBase<Scalar> &mv
00049 ) const
00050 {
00051 return 0!=dynamic_cast<const SpmdVectorSpaceBase<Scalar>*>(&*mv.range());
00052 }
00053
00054 template<class Scalar>
00055 void SpmdMultiVectorSerializer<Scalar>::serialize(
00056 const MultiVectorBase<Scalar>& mv, std::ostream& out
00057 ) const
00058 {
00059 Teuchos::RCP<const SpmdVectorSpaceBase<Scalar> >
00060 mpi_vec_spc
00061 = Teuchos::rcp_dynamic_cast<const SpmdVectorSpaceBase<Scalar> >(mv.range());
00062 out.precision(std::numeric_limits<Scalar>::digits10+4);
00063 if( mpi_vec_spc.get() ) {
00064
00065
00066 const Index
00067 localOffset = mpi_vec_spc->localOffset(),
00068 localSubDim = mpi_vec_spc->localSubDim();
00069 const Range1D localRng( localOffset, localOffset+localSubDim-1 );
00070 ConstDetachedMultiVectorView<Scalar> local_mv(mv,localRng,Range1D());
00071 out << localSubDim << " " << local_mv.numSubCols() << std::endl;
00072 if( binaryMode() ) {
00073
00074 for( Index j = 0; j < local_mv.numSubCols(); ++j )
00075 out.write( reinterpret_cast<const char*>(&local_mv(0,j)), sizeof(Scalar)*localSubDim );
00076 }
00077 else {
00078
00079 for( Index i = 0; i < localSubDim; ++i ) {
00080 out << " " << i;
00081 for( Index j = 0; j < local_mv.numSubCols(); ++j ) {
00082 out << " " << local_mv(i,j);
00083 }
00084 out << std::endl;
00085 }
00086 }
00087 }
00088 else {
00089
00090
00091 TEST_FOR_EXCEPTION( true, std::logic_error, "Does not handle non-SPMD spaces yet" );
00092 }
00093 }
00094
00095 template<class Scalar>
00096 void SpmdMultiVectorSerializer<Scalar>::deserialize(
00097 std::istream& in, MultiVectorBase<Scalar>* mv
00098 ) const
00099 {
00100 Teuchos::RCP<const SpmdVectorSpaceBase<Scalar> >
00101 mpi_vec_spc = Teuchos::rcp_dynamic_cast<const SpmdVectorSpaceBase<Scalar> >(mv->range());
00102 if( mpi_vec_spc.get() ) {
00103
00104
00105 const Index
00106 localOffset = mpi_vec_spc->localOffset(),
00107 localSubDim = mpi_vec_spc->localSubDim();
00108 const Range1D localRng( localOffset, localOffset+localSubDim-1 );
00109 DetachedMultiVectorView<Scalar> local_mv(*mv,localRng,Range1D());
00110 #ifdef TEUCHOS_DEBUG
00111 TEST_FOR_EXCEPTION(
00112 !in, std::logic_error
00113 ,"Error: The input stream given is empty before any reading has began!\n"
00114 "If this stream came from a file, then the file may not exist!"
00115 );
00116 #endif
00117 Index localSubDim_in;
00118 in >> localSubDim_in;
00119 #ifdef TEUCHOS_DEBUG
00120 TEST_FOR_EXCEPTION(
00121 localSubDim != localSubDim_in, std::logic_error
00122 , "Error, localSubDim = "<<localSubDim<<" does not match the read in value of "
00123 "localSubDim_in = "<<localSubDim_in<<"!"
00124 );
00125 #endif
00126 Index numSubCols_in;
00127 in >> numSubCols_in;
00128 #ifdef TEUCHOS_DEBUG
00129 TEST_FOR_EXCEPTION(
00130 local_mv.numSubCols() != numSubCols_in, std::logic_error
00131 , "Error, numSubCols = "<<local_mv.numSubCols()<<" does not match the read in value of "
00132 "numSubCols_in = "<<numSubCols_in<<"!"
00133 );
00134 #endif
00135
00136 in >> std::ws;
00137
00138 if( binaryMode() ) {
00139
00140 for( Index j = 0; j < local_mv.numSubCols(); ++j )
00141 in.read( reinterpret_cast<char*>(&local_mv(0,j)), sizeof(Scalar)*localSubDim );
00142 }
00143 else {
00144
00145 for( Index i = 0; i < localSubDim; ++i ) {
00146 #ifdef TEUCHOS_DEBUG
00147 TEST_FOR_EXCEPTION( !in, std::logic_error, "Error, premature end of input!" );
00148 #endif
00149 Index i_in;
00150 in >> i_in;
00151 #ifdef TEUCHOS_DEBUG
00152 TEST_FOR_EXCEPTION(
00153 i != i_in, std::logic_error
00154 , "Error, i = "<<i<<" does not match the read in value of "
00155 "i_in = "<<i_in<<"!"
00156 );
00157 #endif
00158 for( Index j = 0; j < local_mv.numSubCols(); ++j ) {
00159 #ifdef TEUCHOS_DEBUG
00160 TEST_FOR_EXCEPTION(
00161 !in, std::logic_error
00162 ,"Error: The input stream ran out at j="<<j<<" before"
00163 " reaching the promised " << local_mv.numSubCols()
00164 << " rows of the (multi)vector!"
00165 );
00166 #endif
00167 in >> local_mv(i,j);
00168 }
00169 }
00170 }
00171 }
00172 else {
00173
00174
00175 TEST_FOR_EXCEPTION( true, std::logic_error, "Does not handle non-SPMD spaces yet" );
00176 }
00177 }
00178
00179 }
00180
00181 #endif // THYRA_SPMD_MULTI_VECTOR_SERIALIZER_HPP