Commit c5f64daf authored by Matthieu Martin's avatar Matthieu Martin Committed by Facebook Github Bot

Use more efficient container in Request

Summary:
Use folly Map14 for RequestData and boost flat_set for RequestData's callbacks.
See code comment to explain the choice.

Reviewed By: vipannalla

Differential Revision: D9147805

fbshipit-source-id: adc2d26a7a46c5b7381599ebf44d26fa07e9b775
parent e42d9766
...@@ -159,11 +159,8 @@ void RequestContext::clearContextData(const std::string& val) { ...@@ -159,11 +159,8 @@ void RequestContext::clearContextData(const std::string& val) {
namespace { namespace {
// Execute functor exec for all RequestData in data, which are not in other // Execute functor exec for all RequestData in data, which are not in other
// Similar to std::set_difference but avoid intermediate data structure // Similar to std::set_difference but avoid intermediate data structure
template <typename TExec> template <typename TData, typename TExec>
void exec_set_difference( void exec_set_difference(const TData& data, const TData& other, TExec&& exec) {
const std::set<RequestData*>& data,
const std::set<RequestData*>& other,
TExec&& exec) {
auto diter = data.begin(); auto diter = data.begin();
auto dend = data.end(); auto dend = data.end();
auto oiter = other.begin(); auto oiter = other.begin();
...@@ -230,9 +227,10 @@ RequestContext::setShallowCopyContext() { ...@@ -230,9 +227,10 @@ RequestContext::setShallowCopyContext() {
auto parentLock = parent->state_.rlock(); auto parentLock = parent->state_.rlock();
auto childLock = child->state_.wlock(); auto childLock = child->state_.wlock();
childLock->callbackData_ = parentLock->callbackData_; childLock->callbackData_ = parentLock->callbackData_;
childLock->requestData_.reserve(parentLock->requestData_.size());
for (const auto& entry : parentLock->requestData_) { for (const auto& entry : parentLock->requestData_) {
childLock->requestData_[entry.first] = childLock->requestData_.insert(std::make_pair(
RequestData::constructPtr(entry.second.get()); entry.first, RequestData::constructPtr(entry.second.get())));
} }
} }
......
...@@ -16,10 +16,15 @@ ...@@ -16,10 +16,15 @@
#pragma once #pragma once
// TODO: will remove on top, after fixing all dependencies
#include <map> #include <map>
#include <memory>
#include <set> #include <set>
#include <folly/container/F14Map.h>
#include <folly/sorted_vector_types.h>
#include <memory>
#include <string>
#include <folly/Synchronized.h> #include <folly/Synchronized.h>
namespace folly { namespace folly {
...@@ -167,9 +172,12 @@ class RequestContext { ...@@ -167,9 +172,12 @@ class RequestContext {
DoSetBehaviour behaviour); DoSetBehaviour behaviour);
struct State { struct State {
std::map<std::string, RequestData::SharedPtr> requestData_; // This must be optimized for lookup, its hot path is getContextData
// Note: setContext efficiency relies on this being ordered F14FastMap<std::string, RequestData::SharedPtr> requestData_;
std::set<RequestData*> callbackData_; // This must be optimized for iteration, its hot path is setContext
// We also use the fact that it's ordered to efficiently compute
// the difference with previous context
sorted_vector_set<RequestData*> callbackData_;
}; };
folly::Synchronized<State> state_; folly::Synchronized<State> state_;
}; };
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment