Skip to content

Commit

Permalink
adventures in microoptimization USCiLab#354
Browse files Browse the repository at this point in the history
  • Loading branch information
AzothAmmo authored and WSoptics committed Sep 1, 2017
1 parent 4db0d79 commit b46b2d7
Showing 1 changed file with 16 additions and 5 deletions.
21 changes: 16 additions & 5 deletions include/cereal/details/polymorphic_impl.hpp
Original file line number Diff line number Diff line change
Expand Up @@ -118,7 +118,7 @@ namespace cereal
//! Maps from base type index to a map from derived type index to caster
std::unordered_map<std::type_index, std::unordered_map<std::type_index, std::vector<PolymorphicCaster const*>>> map;

std::unordered_multimap<std::type_index, std::type_index> reverseMap;
std::multimap<std::type_index, std::type_index> reverseMap;

//! Error message used for unregistered polymorphic casts
#define UNREGISTERED_POLYMORPHIC_CAST_EXCEPTION(LoadSave) \
Expand Down Expand Up @@ -267,12 +267,23 @@ namespace cereal
};

std::stack<std::type_index> parentStack; // Holds the parent nodes to be processed
std::unordered_set<std::type_index> dirtySet; // Marks child nodes that have been changed
std::vector<std::type_index> dirtySet; // Marks child nodes that have been changed
std::unordered_set<std::type_index> processedParents; // Marks parent nodes that have been processed

// Checks if a child has been marked dirty
auto isDirty = [&](std::type_index const & c)
{
auto const dirtySetSize = dirtySet.size();
for( size_t i = 0; i < dirtySetSize; ++i )
if( dirtySet[i] == c )
return true;

return false;
};

// Begin processing the base key and mark derived as dirty
parentStack.push( baseKey );
dirtySet.emplace( derivedKey );
dirtySet.emplace_back( derivedKey );

while( !parentStack.empty() )
{
Expand All @@ -286,7 +297,7 @@ namespace cereal
for( auto const & childPair : baseMap[parent] )
{
const auto child = childPair.first;
if( dirtySet.count( child ) && baseMap.count( child ) )
if( isDirty( child ) && baseMap.count( child ) )
{
auto parentChildPath = checkRelation( parent, child );

Expand Down Expand Up @@ -345,7 +356,7 @@ namespace cereal
}

// Mark current parent as modified
dirtySet.insert( parent );
dirtySet.emplace_back( parent );

// Insert all parents of the current parent node that haven't yet been processed
auto parentRange = reverseMap.equal_range( parent );
Expand Down

0 comments on commit b46b2d7

Please sign in to comment.