librostlab
1.0.20
|
00001 /* 00002 Copyright (C) 2011 Laszlo Kajan, Technical University of Munich, Germany 00003 00004 This file is part of librostlab. 00005 00006 librostlab is free software: you can redistribute it and/or modify 00007 it under the terms of the GNU Lesser General Public License as published by 00008 the Free Software Foundation, either version 3 of the License, or 00009 (at your option) any later version. 00010 00011 This program is distributed in the hope that it will be useful, 00012 but WITHOUT ANY WARRANTY; without even the implied warranty of 00013 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 00014 GNU Lesser General Public License for more details. 00015 00016 You should have received a copy of the GNU Lesser General Public License 00017 along with this program. If not, see <http://www.gnu.org/licenses/>. 00018 */ 00019 #ifndef ROSTLAB_STDIO 00020 #define ROSTLAB_STDIO 1 00021 00022 #include <stdint.h> 00023 #include <stdio.h> 00024 00025 namespace rostlab { 00026 00027 template<typename _Tp> 00028 inline void fwrite( const _Tp& __v, FILE* __out ){ if( ::fwrite( &__v, sizeof(__v), 1, __out ) != 1 ) throw rostlab::runtime_error( strerror(errno) ); } 00029 template<typename _Tp, typename _Alloc> 00030 inline void fwrite( const vector<_Tp,_Alloc>& __v, FILE* __out ) 00031 { 00032 if( __v.size() > 0xffff ){ ostringstream s; s << __v.size() << " is out of range (0-65535)"; throw rostlab::range_error( s.str() ); } 00033 fwrite<uint16_t>( __v.size(), __out ); 00034 if( ::fwrite( __v.data(), sizeof(typename vector<_Tp,_Alloc>::value_type), __v.size(), __out ) != __v.size() ) throw rostlab::runtime_error( strerror(errno) ); 00035 } 00036 template<> 00037 inline void fwrite<string>( const string& __str, FILE* __out ) 00038 { 00039 fwrite<uint16_t>( __str.length(), __out ); 00040 if( !__str.length() ) return; 00041 if( ::fwrite( __str.c_str(), sizeof( string::value_type ), __str.length(), __out ) != __str.length() ) throw rostlab::runtime_error( strerror(errno) ); 00042 } 00043 inline void fwrite( const char* __c, FILE* __out ) { fwrite( string(__c), __out ); } 00044 00045 template<typename _Tp> 00046 inline void fread( _Tp& __v, FILE* __in ) 00047 { 00048 if( ::fread( &__v, sizeof(__v), 1, __in ) != 1 ) throw rostlab::runtime_error( strerror(errno) ); 00049 } 00050 template<typename _Tp, typename _Alloc> 00051 inline void fread( vector<_Tp, _Alloc>& __v, FILE* __in ) 00052 { 00053 uint16_t size; fread( size, __in); 00054 __v = vector<_Tp, _Alloc>(size); 00055 if( ::fread( __v.data(), sizeof(typename vector<_Tp, _Alloc>::value_type), __v.size(), __in ) != __v.size() ) throw rostlab::runtime_error( strerror(errno) ); 00056 } 00057 template<> 00058 inline void fread<string>( string& __v, FILE* __in ) 00059 { 00060 uint16_t strlen; fread( strlen, __in); 00061 if( !strlen ){ __v = string(); return; } 00062 00063 string::value_type buf[ sizeof( string::value_type ) * strlen ]; 00064 size_t managed_to_read = ::fread( buf, sizeof( string::value_type ), strlen, __in ); 00065 if( managed_to_read != strlen ) throw rostlab::runtime_error( strerror(errno) ); 00066 __v = string( buf, managed_to_read ); 00067 } 00068 // This must come last - uses the others. 00069 template<typename _Tp> 00070 inline _Tp fread( FILE* __in ){ _Tp ret; fread( ret, __in ); return ret; } 00071 00072 } // namespace rostlab 00073 00074 #endif // ROSTLAB_STDIO 00075 // vim:et:ts=4:ai: