SizePolicy.h 2.6 KB

12345678910111213141516171819202122232425262728293031323334353637383940414243444546474849505152535455565758596061626364656667686970717273747576777879808182838485
  1. //-------------------------------------------------------------------------------------------------------
  2. // Copyright (C) Microsoft. All rights reserved.
  3. // Licensed under the MIT license. See LICENSE.txt file in the project root for full license information.
  4. //-------------------------------------------------------------------------------------------------------
  5. #pragma once
  6. struct PrimePolicy
  7. {
  8. __inline static uint GetBucket(hash_t hashCode, int size)
  9. {
  10. uint targetBucket = hashCode % size;
  11. return targetBucket;
  12. }
  13. __inline static uint GetSize(uint capacity)
  14. {
  15. return GetPrime(capacity);
  16. }
  17. private:
  18. static bool IsPrime(uint candidate);
  19. static uint GetPrime(uint min);
  20. };
  21. struct PowerOf2Policy
  22. {
  23. __inline static uint GetBucket(hash_t hashCode, int size)
  24. {
  25. AssertMsg(Math::IsPow2(size), "Size is not a power of 2.");
  26. uint targetBucket = hashCode & (size-1);
  27. return targetBucket;
  28. }
  29. /// Returns a size that is power of 2 and
  30. /// greater than specified capacity.
  31. __inline static uint GetSize(size_t minCapacity_t)
  32. {
  33. AssertMsg(minCapacity_t <= MAXINT32, "the next higher power of 2 must fit in uint32");
  34. uint minCapacity = static_cast<uint>(minCapacity_t);
  35. if(minCapacity <= 0)
  36. {
  37. return 4;
  38. }
  39. if (Math::IsPow2(minCapacity))
  40. {
  41. return minCapacity;
  42. }
  43. else
  44. {
  45. return 1 << (Math::Log2(minCapacity) + 1);
  46. }
  47. }
  48. };
  49. #ifndef JD_PRIVATE
  50. template <class SizePolicy, uint averageChainLength = 2, uint growthRateNumerator = 2, uint growthRateDenominator = 1, uint minBucket = 4>
  51. struct DictionarySizePolicy
  52. {
  53. CompileAssert(growthRateNumerator > growthRateDenominator);
  54. CompileAssert(growthRateDenominator != 0);
  55. __inline static uint GetBucket(hash_t hashCode, uint bucketCount)
  56. {
  57. return SizePolicy::GetBucket(hashCode, bucketCount);
  58. }
  59. __inline static uint GetNextSize(uint minCapacity)
  60. {
  61. uint nextSize = minCapacity * growthRateNumerator / growthRateDenominator;
  62. return (growthRateDenominator != 1 && nextSize <= minCapacity)? minCapacity + 1 : nextSize;
  63. }
  64. __inline static uint GetBucketSize(uint size)
  65. {
  66. if (minBucket * averageChainLength >= size)
  67. {
  68. return SizePolicy::GetSize(minBucket);
  69. }
  70. return SizePolicy::GetSize((size + (averageChainLength - 1)) / averageChainLength);
  71. }
  72. };
  73. typedef DictionarySizePolicy<PrimePolicy> PrimeSizePolicy;
  74. typedef DictionarySizePolicy<PowerOf2Policy> PowerOf2SizePolicy;
  75. #endif