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 #include <fstream>
00026 #include <stdexcept>
00027 #include <string>
00028 #include <vector>
00029
00030 #include <boost/lexical_cast.hpp>
00031 #include <boost/shared_ptr.hpp>
00032
00033 #include "../../common/WAssert.h"
00034 #include "../../common/WIOTools.h"
00035 #include "../../common/WLogger.h"
00036 #include "../../common/WStringUtils.h"
00037 #include "../exceptions/WDHException.h"
00038 #include "../exceptions/WDHIOFailure.h"
00039 #include "WReader.h"
00040 #include "WReaderMatrixSymVTK.h"
00041
00042 WReaderMatrixSymVTK::WReaderMatrixSymVTK( std::string fname )
00043 : WReader( fname )
00044 {
00045 }
00046
00047 void WReaderMatrixSymVTK::readTable( boost::shared_ptr< std::vector< double > > table ) const
00048 {
00049 WAssert( table->size() == 0, "Non-zero size indicates an error, since the vector will be filled IN HERE." );
00050
00051
00052
00053 std::ifstream ifs;
00054 ifs.open( m_fname.c_str(), std::ifstream::in | std::ifstream::binary );
00055 WAssert( ifs && !ifs.bad(), "" );
00056
00057 std::vector< std::string > header;
00058 std::string line;
00059 try
00060 {
00061 for( int i = 0; i < 4; ++i )
00062 {
00063 std::getline( ifs, line );
00064 if( !ifs.good() )
00065 {
00066 throw WDHException( std::string( "Unexpected end of file: " + m_fname ) );
00067 }
00068 header.push_back( line );
00069 }
00070 }
00071 catch( const std::ios_base::failure &e )
00072 {
00073 throw WDHIOFailure( std::string( "Reading first 4 lines of '" + m_fname + "': " + e.what() ) );
00074 }
00075 if( header[0] != "# vtk DataFile Version 3.0" )
00076 {
00077 wlog::warn( "WReaderMatrixSymVTK" ) << "Wrong version string in file header found, expected: "
00078 "\"# vtk DataFile Version 3.0\" but got: " << header[0];
00079 }
00080 if( header[2] != "BINARY" )
00081 {
00082 wlog::error( "WReaderMatrixSymVTK" ) << "Wrong data format: BINARY expected but got: " << header[2];
00083 throw WDHIOFailure( "Error reading file '" + m_fname + " invalid binary format." );
00084 }
00085 if( header[3] != "FIELD WMatrixSym 1" )
00086 {
00087 wlog::error( "WReaderMatrixSymVTK" ) << "Wrong field desc in file header found: " << header[3] << " but expected: \"FIELD WMatrixSym 1\"";
00088 throw WDHIOFailure( "Error reading file '" + m_fname + " invalid VTK field name." );
00089 }
00090
00091 try
00092 {
00093 std::getline( ifs, line );
00094 }
00095 catch( const std::ios_base::failure &e )
00096 {
00097 throw WDHIOFailure( std::string( "Error reading ELEMENTS field '" + m_fname + "': " + e.what() ) );
00098 }
00099 namespace su = string_utils;
00100 size_t numDistances = 0;
00101 std::vector< std::string > tokens = su::tokenize( line );
00102 if( tokens.size() != 4 || su::toLower( tokens.at( 3 ) ) != "float" )
00103 {
00104 throw WDHException( std::string( "Invalid ELEMENTS declaration: " + line ) );
00105 }
00106 try
00107 {
00108 numDistances = boost::lexical_cast< size_t >( tokens.at( 1 ) );
00109 }
00110 catch( const boost::bad_lexical_cast &e )
00111 {
00112 throw WDHException( std::string( "Invalid number of elements: " + tokens.at( 1 ) ) );
00113 }
00114
00115 float *data = new float[ numDistances ];
00116 try
00117 {
00118 ifs.read( reinterpret_cast< char* >( data ), sizeof( float ) * numDistances );
00119 }
00120 catch( const std::ios_base::failure &e )
00121 {
00122 throw WDHIOFailure( std::string( "Error reading elements in VTK ELEMENTS field '" + m_fname + "': " + e.what() ) );
00123 }
00124
00125
00126 switchByteOrderOfArray( data, numDistances );
00127
00128 for( size_t i = 0; i < numDistances; ++i )
00129 {
00130 table->push_back( static_cast< double >( data[ i ] ) );
00131 }
00132
00133 delete[] data;
00134 }