mirror of
https://github.com/facebook/react-native.git
synced 2025-11-01 09:14:26 +00:00
df229590b2
Summary: This part of the codebase is very perf sensitive and designed to work without exceptions enabled. Most of the method was `noexcept` all the time, but some of those missing that by mistake. Reviewed By: sammy-SC Differential Revision: D17629426 fbshipit-source-id: b311e4b7eff8e2b7cf29518288480d3a812dda44
91 lines
2.2 KiB
C++
91 lines
2.2 KiB
C++
/**
|
|
* Copyright (c) Facebook, Inc. and its affiliates.
|
|
*
|
|
* This source code is licensed under the MIT license found in the
|
|
* LICENSE file in the root directory of this source tree.
|
|
*/
|
|
|
|
#include "RawPropsKeyMap.h"
|
|
|
|
#include <cassert>
|
|
#include <cstdlib>
|
|
#include <cstring>
|
|
|
|
namespace facebook {
|
|
namespace react {
|
|
|
|
int RawPropsKeyMap::comparator(void const *lhs, void const *rhs) noexcept {
|
|
auto a = static_cast<RawPropsKeyMap::Item const *>(lhs);
|
|
auto b = static_cast<RawPropsKeyMap::Item const *>(rhs);
|
|
|
|
if (a->length != b->length) {
|
|
return a->length - b->length;
|
|
}
|
|
|
|
return std::memcmp(a->name, b->name, a->length);
|
|
}
|
|
|
|
void RawPropsKeyMap::insert(
|
|
RawPropsKey const &key,
|
|
RawPropsValueIndex value) noexcept {
|
|
auto item = Item{};
|
|
item.value = value;
|
|
key.render(item.name, &item.length);
|
|
items_.push_back(item);
|
|
}
|
|
|
|
void RawPropsKeyMap::reindex() noexcept {
|
|
// Sorting `items_` by property names length and then lexicographically.
|
|
std::qsort(
|
|
items_.data(),
|
|
items_.size(),
|
|
sizeof(decltype(items_)::value_type),
|
|
&RawPropsKeyMap::comparator);
|
|
|
|
buckets_.resize(kPropNameLengthHardCap);
|
|
|
|
auto length = RawPropsPropNameLength{0};
|
|
for (auto i = 0; i < items_.size(); i++) {
|
|
auto &item = items_[i];
|
|
if (item.length != length) {
|
|
for (auto j = length; j < item.length; j++) {
|
|
buckets_[j] = i;
|
|
}
|
|
length = item.length;
|
|
}
|
|
}
|
|
|
|
for (auto j = length; j < buckets_.size(); j++) {
|
|
buckets_[j] = items_.size();
|
|
}
|
|
}
|
|
|
|
RawPropsValueIndex RawPropsKeyMap::at(
|
|
char const *name,
|
|
RawPropsPropNameLength length) noexcept {
|
|
assert(length > 0);
|
|
assert(length < kPropNameLengthHardCap);
|
|
// 1. Find the bucket.
|
|
auto lower = int{buckets_[length - 1]};
|
|
auto upper = int{buckets_[length]} - 1;
|
|
assert(lower - 1 <= upper);
|
|
|
|
// 2. Binary search in the bucket.
|
|
while (lower <= upper) {
|
|
auto median = (lower + upper) / 2;
|
|
auto condition = std::memcmp(items_[median].name, name, length);
|
|
if (condition < 0) {
|
|
lower = median + 1;
|
|
} else if (condition == 0) {
|
|
return items_[median].value;
|
|
} else /* if (condition > 0) */ {
|
|
upper = median - 1;
|
|
}
|
|
}
|
|
|
|
return kRawPropsValueIndexEmpty;
|
|
}
|
|
|
|
} // namespace react
|
|
} // namespace facebook
|