store and restore individual elements of vectors if the data is not densely packed in the vector

This commit is contained in:
Max Lyon
2021-03-02 02:11:18 +01:00
parent c1f3a4d3d1
commit 657128e6d4
2 changed files with 41 additions and 16 deletions

View File

@@ -347,11 +347,11 @@ struct binary< std::vector< T > > {
for(auto v : _v) for(auto v : _v)
{ {
size += binary<T>::size_of(v); size += binary<T>::size_of(v);
if(_store_size) }
{ if(_store_size)
unsigned int N = _v.size(); {
size += binary<unsigned int>::size_of(); unsigned int N = _v.size();
} size += binary<unsigned int>::size_of();
} }
return size; return size;
@@ -370,11 +370,24 @@ struct binary< std::vector< T > > {
if (_swap) if (_swap)
bytes += std::accumulate( _v.begin(), _v.end(), static_cast<size_t>(0), bytes += std::accumulate( _v.begin(), _v.end(), static_cast<size_t>(0),
FunctorStore<elem_type>(_os,_swap) ); FunctorStore<elem_type>(_os,_swap) );
else { else
auto bytes_of_vec = size_of(_v, false); {
bytes += bytes_of_vec; auto elem_size = binary<elem_type>::size_of();
if (_v.size() > 0) if (elem_size != IO::UnknownSize && elem_size == sizeof(elem_type))
_os.write( reinterpret_cast<const char*>(&_v[0]), bytes_of_vec); {
// size of all elements is known, equal, and densely packed in vector.
// Just store vector data
auto bytes_of_vec = size_of(_v, false);
bytes += bytes_of_vec;
if (_v.size() > 0)
_os.write( reinterpret_cast<const char*>(&_v[0]), bytes_of_vec);
}
else
{
// store individual elements
for (const auto& v : _v)
bytes += binary<elem_type>::store(_os, v, _swap);
}
} }
return _os.good() ? bytes : 0; return _os.good() ? bytes : 0;
} }
@@ -395,10 +408,22 @@ struct binary< std::vector< T > > {
FunctorRestore<elem_type>(_is, _swap) ); FunctorRestore<elem_type>(_is, _swap) );
else else
{ {
auto bytes_of_vec = size_of(_v, false); auto elem_size = binary<elem_type>::size_of();
bytes += bytes_of_vec; if (elem_size != IO::UnknownSize && elem_size == sizeof(elem_type))
if (_v.size() > 0) {
_is.read( reinterpret_cast<char*>(&_v[0]), bytes_of_vec ); // size of all elements is known, equal, and densely packed in vector.
// Just restore vector data
auto bytes_of_vec = size_of(_v, false);
bytes += bytes_of_vec;
if (_v.size() > 0)
_is.read( reinterpret_cast<char*>(&_v[0]), bytes_of_vec );
}
else
{
// restore individual elements
for (auto& v : _v)
bytes += binary<elem_type>::restore(_is, v, _swap);
}
} }
return _is.good() ? bytes : 0; return _is.good() ? bytes : 0;
} }

View File

@@ -161,8 +161,8 @@ public:
virtual size_t restore( std::istream& _istr, bool _swap ) override virtual size_t restore( std::istream& _istr, bool _swap ) override
{ {
if ( IO::is_streamable<vector_type>() && element_size() != IO::UnknownSize ) if ( IO::is_streamable<vector_type>() && element_size() != IO::UnknownSize)
return IO::restore(_istr, data_, _swap, false); //does not need to restore its length return IO::restore(_istr, data_, _swap, false); //does not need to restore its length
size_t bytes = 0; size_t bytes = 0;
for (size_t i=0; i<n_elements(); ++i) for (size_t i=0; i<n_elements(); ++i)