RBGen  Version of the Day
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Groups Pages
RBGen_BurkardtFileIOHandler.cpp
1 
2 #include "RBGen_BurkardtFileIOHandler.h"
3 #include "RBGen_ConfigDefs.h"
4 
5 #include "Epetra_BLAS.h"
6 #include "Epetra_Export.h"
7 #include "Epetra_Import.h"
8 #include "Epetra_Map.h"
9 #include "Epetra_Vector.h"
10 #include "Epetra_MultiVector.h"
11 
12 #include "Teuchos_Utils.hpp"
13 #include "Teuchos_Assert.hpp"
14 
15 #ifdef EPETRA_MPI
16 #include "Epetra_MpiComm.h"
17 #else
18 #include "Epetra_SerialComm.h"
19 #endif
20 
21 
22 namespace RBGen {
23 
25  : num_nodes(0), isInit(false)
26  {
27  }
28 
30  {
31 
32 #ifdef EPETRA_MPI
33  Epetra_MpiComm comm( MPI_COMM_WORLD );
34 #else
35  Epetra_SerialComm comm;
36 #endif
37 
38  // Get the "File I/O" sublist.
39  Teuchos::ParameterList& fileio_params = params->sublist( "File IO" );
40 
41  if( fileio_params.isParameter("Burkardt Data Format File") )
42  {
43  std::string format_file = Teuchos::getParameter<std::string>( fileio_params, "Burkardt Data Format File" );
44  //
45  // The first processor get the number of nodes from the data format file and then broadcasts it.
46  //
47  if ( comm.MyPID() == 0 )
48  num_nodes = data_size( format_file );
49  comm.Broadcast( &num_nodes, 1, 0 );
50  // if (!num_nodes) { TO DO: THROW EXCEPTION! }
51  isInit = true;
52  }
53  else
54  {
55  // Can't find the data size or data format file
56  isInit = false;
57  TEUCHOS_TEST_FOR_EXCEPTION(true, std::runtime_error, "Cannot find the data size or data format file 'Burkardt Data Format File'!");
58  }
59 
60  // Get the input path.
61  in_path = "";
62  if ( fileio_params.isParameter( "Data Input Path" ) ) {
63  in_path = Teuchos::getParameter<std::string>( fileio_params, "Data Input Path" );
64  }
65 
66  // Get the output path.
67  out_path = "";
68  if ( fileio_params.isParameter( "Data Output Path" ) ) {
69  out_path = Teuchos::getParameter<std::string>( fileio_params, "Data Output Path" );
70  }
71 
72  // This file i/o handler is not initialized.
73  isInit = true;
74  }
75 
76  Teuchos::RCP<Epetra_MultiVector> BurkardtFileIOHandler::Read( const std::vector<std::string>& filenames )
77  {
78 
80 
81  if (isInit) {
82 
83 #ifdef EPETRA_MPI
84  Epetra_MpiComm comm( MPI_COMM_WORLD );
85 #else
86  Epetra_SerialComm comm;
87 #endif
88 
89  int i,j;
90  int num_vecs = filenames.size();
91  int dim = 2*num_nodes;
92  int* index = new int[ num_nodes ];
93  double *u = new double[ num_nodes ];
94  double *v = new double[ num_nodes ];
95  Epetra_Map Map( dim, 0, comm );
96  Epetra_Map* Proc0Map;
97  Epetra_Vector* col_newMV;
98  newMV = Teuchos::rcp( new Epetra_MultiVector( Map, num_vecs ) );
99  //
100  // Create map putting all elements of vector on Processor 0.
101  //
102  if ( comm.MyPID() == 0 ) {
103  Proc0Map = new Epetra_Map( dim, dim, 0, comm );
104  } else {
105  Proc0Map = new Epetra_Map( dim, 0, 0, comm );
106  }
107  Epetra_Vector Proc0Vector( *Proc0Map );
108  //
109  // Create an importer to get this information into the global Epetra_Vector
110  //
111  Epetra_Import importer( Map, *Proc0Map );
112  //
113  // Processor 0 reads each file and then creates a local Epetra_Vector, which will be
114  // imported into the i-th column of the Epetra_MultiVector.
115  //
116  for ( i=0; i<num_vecs; i++ ) {
117  //
118  // Get column of Epetra_MultiVector in terms of Epetra_Vector.
119  //
120  col_newMV = (*newMV)( i );
121  //
122  // Let Processor 0 fill in the Epetra_Vector.
123  //
124  if ( comm.MyPID() == 0 ) {
125  //
126  // Read in vectors from the next file.
127  //
128  std::string temp_filename = in_path + filenames[i];
129  read_vec( temp_filename.c_str(), num_nodes, u, v );
130  //
131  // The storage of the velocity vectors is interleaved.
132  //
133  // Place the first component in the vector.
134  for ( j=0; j<num_nodes; j++ )
135  index[j] = 2*j;
136  Proc0Vector.ReplaceGlobalValues( num_nodes, u, index );
137 
138  // Place the second component in the vector.
139  for ( j=0; j<num_nodes; j++ )
140  index[j] = 2*j + 1;
141  Proc0Vector.ReplaceGlobalValues( num_nodes, v, index );
142  }
143  //
144  // Import the information.
145  //
146  col_newMV->Import(Proc0Vector, importer, Add);
147  }
148  //
149  // Clean up
150  delete Proc0Map;
151  delete [] index;
152  delete [] u;
153  delete [] v;
154 
155  }
156  else {
157  TEUCHOS_TEST_FOR_EXCEPTION(true, std::runtime_error, "File I/O handler is not initialized!");
158  }
159  // Return.
160  return newMV;
161  }
162 
163  void BurkardtFileIOHandler::Write( const Teuchos::RCP<const Epetra_MultiVector>& MV, const std::string& filename )
164  {
165  if (isInit) {
166 
167 #ifdef EPETRA_MPI
168  Epetra_MpiComm comm( MPI_COMM_WORLD );
169 #else
170  Epetra_SerialComm comm;
171 #endif
172 
173  int i;
174  int num_vecs = MV->NumVectors();
175  int dim = 2*num_nodes;
176  double *u = 0, *v = 0;
177  Epetra_Map Map( dim, 0, comm );
178  Epetra_Map* Proc0Map;
179  Epetra_BLAS blas;
180  const Epetra_Vector* col_newMV;
181  std::string out_file;
182  int num_places = (int)::ceil( ::log10( (double)(num_vecs) ) );
183  //
184  // Create map putting all elements of vector on Processor 0.
185  //
186  if ( comm.MyPID() == 0 ) {
187  Proc0Map = new Epetra_Map( dim, dim, 0, comm );
188  u = new double[ num_nodes ];
189  v = new double[ num_nodes ];
190  } else {
191  Proc0Map = new Epetra_Map( dim, 0, 0, comm );
192  }
193  Epetra_Vector Proc0Vector( *Proc0Map );
194  //
195  // Create an exporter to get the global Epetra_Vector to a local Epetra_Vector.
196  //
197  Epetra_Export exporter( MV->Map(), *Proc0Map );
198  //
199  i = 0;
200  while ( i < num_vecs ) {
201  //
202  // Get column of Epetra_MultiVector in terms of Epetra_Vector.
203  //
204  col_newMV = (*MV)( i );
205  //
206  Proc0Vector.Export(*col_newMV, exporter, Insert);
207  //
208  // Copy the singular vector into holders
209  //
210  i++; // Increment counter here to get right number in output filename!
211  //
212  if ( comm.MyPID() == 0 ) {
213  blas.COPY( num_nodes, &Proc0Vector[0], u, 2, 1 );
214  blas.COPY( num_nodes, &Proc0Vector[0]+1, v, 2, 1 );
215  //
216  // Determine next filename.
217  //
218  out_file = out_path + filename;
219  int curr_places = (int)::ceil( ::log10( (double)(i) ) );
220 
221  // Put in the right number of zeros.
222  for (int j=curr_places; j<num_places; j++) {
223  out_file += "0";
224  }
225 
226  // Add the file number.
227  out_file += Teuchos::Utils::toString( i );
228 
229  //
230  // Write out.
231  //
232  write_vec( out_file, num_nodes, u, v );
233  }
234  }
235  //
236  // Clean up.
237  //
238  if ( u ) delete [] u;
239  if ( v ) delete [] v;
240  delete Proc0Map;
241  }
242  else {
243  TEUCHOS_TEST_FOR_EXCEPTION(true, std::runtime_error, "File I/O handler is not initialized!");
244  }
245  }
246 
247  /* -----------------------------------------------------------------------------
248  GET NUMBER OF NODES IN THE DATA FROM A FORMAT FILE
249  ----------------------------------------------------------------------------- */
250  int BurkardtFileIOHandler::data_size( const std::string filename )
251  {
252  FILE *in_file ;
253  char temp_str[100];
254  int i=0;
255 
256  if ( (in_file = fopen( filename.c_str(), "r")) == NULL ) {
257  fprintf(stderr,"Error: Cannot open file: %s\n",filename.c_str());
258  return( -1 );
259  }
260  //
261  // Count how many lines are in the file.
262  //
263  while( fgets( temp_str, 100, in_file ) != NULL ) { i++; }
264 
265  fclose(in_file);
266  return( i );
267  }
268 
269  /* -----------------------------------------------------------------------------
270  READ IN A DATA PAIR FROM AN INPUT FILE
271  ----------------------------------------------------------------------------- */
272  int BurkardtFileIOHandler::read_vec( const std::string filename, int n_equations, double *x, double *y )
273  {
274  FILE *in_file ;
275  int i;
276 
277  if ( !x ) {
278  fprintf(stderr,"Error: pointer to x vector is NULL \n");
279  return(-1);
280  }
281 
282  if ( (in_file = fopen( filename.c_str(), "r")) == NULL ) {
283  fprintf(stderr,"Error: Cannot open file: %s\n", filename.c_str());
284  return(-1);
285  }
286 
287  if ( y ) {
288  for (i=0; i< n_equations; i++)
289  fscanf(in_file, "%lf%lf", x+i, y+i);
290  }
291  else {
292  for(i=0; i< n_equations; i++)
293  fscanf(in_file, "%lf", x+i);
294  }
295  fclose(in_file);
296  return( 0 );
297  /* end read_vec */
298  }
299 
300  /* -----------------------------------------------------------------------------
301  WRITE OUT A DATA PAIR TO AN INPUT FILE
302  ----------------------------------------------------------------------------- */
303  int BurkardtFileIOHandler::write_vec( const std::string filename, int n_equations, double *x, double *y )
304  {
305  FILE *out_file ;
306  int i;
307 
308  if ( !x ) {
309  fprintf(stderr,"Error: pointer to x vector is NULL \n");
310  return( -1 );
311  }
312 
313  if ( (out_file = fopen( filename.c_str(), "w")) == NULL ) {
314  fprintf(stderr,"Error: Cannot open file: %s\n",filename.c_str());
315  return( -1 );
316  }
317 
318  if ( y ) {
319  for (i=0; i< n_equations; i++)
320  fprintf(out_file, "%25.15e%25.15e\n", x[i], y[i]) ;
321  }
322  else {
323  for(i=0; i< n_equations; i++)
324  fprintf(out_file, "%25.15e\n", x[i]) ;
325  }
326 
327  fclose(out_file);
328  return( 0 );
329  /* end write_vec */
330  }
331 
332 } // namespace RBGen
333 
334 
#define TEUCHOS_TEST_FOR_EXCEPTION(throw_exception_test, Exception, msg)
int MyPID() const
static std::string toString(const double &x)
int ReplaceGlobalValues(int NumEntries, const double *Values, const int *Indices)
bool isParameter(const std::string &name) const
TEUCHOS_DEPRECATED RCP< T > rcp(T *p, Dealloc_T dealloc, bool owns_mem)
Teuchos::RCP< Epetra_MultiVector > Read(const std::vector< std::string > &filenames)
Method for reading multiple files and putting them into an Epetra_MultiVector.
ParameterList & sublist(const std::string &name, bool mustAlreadyExist=false, const std::string &docString="")
void COPY(const int N, const float *X, float *Y, const int INCX=1, const int INCY=1) const
int Broadcast(double *MyVals, int Count, int Root) const
void Initialize(const Teuchos::RCP< Teuchos::ParameterList > &params)
Initialize file reader using.
void Write(const Teuchos::RCP< const Epetra_MultiVector > &MV, const std::string &filename)
Method for writing one Epetra_MultiVector into a file.