comparator.cc 2.1 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475
  1. // Copyright (c) 2011 The LevelDB Authors. All rights reserved.
  2. // Use of this source code is governed by a BSD-style license that can be
  3. // found in the LICENSE file. See the AUTHORS file for names of contributors.
  4. #include "leveldb/comparator.h"
  5. #include <algorithm>
  6. #include <cstdint>
  7. #include <string>
  8. #include <type_traits>
  9. #include "leveldb/slice.h"
  10. #include "util/logging.h"
  11. #include "util/no_destructor.h"
  12. namespace leveldb {
  13. Comparator::~Comparator() = default;
  14. namespace {
  15. class BytewiseComparatorImpl : public Comparator {
  16. public:
  17. BytewiseComparatorImpl() = default;
  18. const char* Name() const override { return "leveldb.BytewiseComparator"; }
  19. int Compare(const Slice& a, const Slice& b) const override {
  20. return a.compare(b);
  21. }
  22. void FindShortestSeparator(std::string* start,
  23. const Slice& limit) const override {
  24. // Find length of common prefix
  25. size_t min_length = std::min(start->size(), limit.size());
  26. size_t diff_index = 0;
  27. while ((diff_index < min_length) &&
  28. ((*start)[diff_index] == limit[diff_index])) {
  29. diff_index++;
  30. }
  31. if (diff_index >= min_length) {
  32. // Do not shorten if one string is a prefix of the other
  33. } else {
  34. uint8_t diff_byte = static_cast<uint8_t>((*start)[diff_index]);
  35. if (diff_byte < static_cast<uint8_t>(0xff) &&
  36. diff_byte + 1 < static_cast<uint8_t>(limit[diff_index])) {
  37. (*start)[diff_index]++;
  38. start->resize(diff_index + 1);
  39. assert(Compare(*start, limit) < 0);
  40. }
  41. }
  42. }
  43. void FindShortSuccessor(std::string* key) const override {
  44. // Find first character that can be incremented
  45. size_t n = key->size();
  46. for (size_t i = 0; i < n; i++) {
  47. const uint8_t byte = (*key)[i];
  48. if (byte != static_cast<uint8_t>(0xff)) {
  49. (*key)[i] = byte + 1;
  50. key->resize(i + 1);
  51. return;
  52. }
  53. }
  54. // *key is a run of 0xffs. Leave it alone.
  55. }
  56. };
  57. } // namespace
  58. const Comparator* BytewiseComparator() {
  59. static NoDestructor<BytewiseComparatorImpl> singleton;
  60. return singleton.get();
  61. }
  62. } // namespace leveldb