Chromium Code Reviews| OLD | NEW |
|---|---|
| 1 // Copyright 2014 The Chromium Authors. All rights reserved. | 1 // Copyright 2014 The Chromium Authors. All rights reserved. |
| 2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
| 3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
| 4 | 4 |
| 5 #ifndef COMPONENTS_COPRESENCE_TIMED_MAP_ | 5 #ifndef COMPONENTS_COPRESENCE_TIMED_MAP_H_ |
| 6 #define COMPONENTS_COPRESENCE_TIMED_MAP_ | 6 #define COMPONENTS_COPRESENCE_TIMED_MAP_H_ |
| 7 | 7 |
| 8 #include <map> | 8 #include <map> |
| 9 #include <queue> | 9 #include <queue> |
| 10 #include <utility> | 10 #include <utility> |
| 11 #include <vector> | 11 #include <vector> |
| 12 | 12 |
| 13 #include "base/macros.h" | 13 #include "base/macros.h" |
| 14 #include "base/time/default_tick_clock.h" | 14 #include "base/time/default_tick_clock.h" |
| 15 #include "base/time/tick_clock.h" | 15 #include "base/time/tick_clock.h" |
| 16 #include "base/time/time.h" | 16 #include "base/time/time.h" |
| 17 #include "base/timer/timer.h" | 17 #include "base/timer/timer.h" |
| 18 | 18 |
| 19 namespace copresence { | 19 namespace copresence { |
| 20 | 20 |
| 21 // TimedMap is a map with the added functionality of clearing any | 21 // TimedMap is a map with the added functionality of clearing any |
| 22 // key/value pair after its specified lifetime is over. | 22 // key/value pair after its specified lifetime is over. |
| 23 template <typename KeyType, typename ValueType> | 23 template <typename KeyType, typename ValueType> |
| 24 class TimedMap { | 24 class TimedMap { |
| 25 public: | 25 public: |
| 26 TimedMap(const base::TimeDelta& lifetime, size_t max_elements) | 26 TimedMap(const base::TimeDelta& lifetime, size_t max_elements) |
| 27 : kEmptyValue(ValueType()), | 27 : kEmptyValue(ValueType()), |
| 28 clock_(new base::DefaultTickClock()), | 28 clock_(new base::DefaultTickClock()), |
| 29 lifetime_(lifetime), | 29 lifetime_(lifetime), |
| 30 max_elements_(max_elements) { | 30 max_elements_(max_elements) { |
| 31 timer_.Start(FROM_HERE, lifetime_, this, &TimedMap::ClearExpiredTokens); | 31 timer_.Start(FROM_HERE, lifetime_, this, &TimedMap::ClearExpiredTokens); |
| 32 } | 32 } |
| 33 | 33 |
| 34 ~TimedMap() {} | 34 ~TimedMap() { |
| 35 delete clock_; | |
|
rkc
2014/08/09 06:41:42
No reason for this clock to not be a scoped_ptr. L
Charlie
2014/08/09 07:10:40
Done.
| |
| 36 } | |
| 35 | 37 |
| 36 void Add(const KeyType& key, const ValueType& value) { | 38 void Add(const KeyType& key, const ValueType& value) { |
| 37 map_[key] = value; | 39 map_[key] = value; |
| 38 expiry_queue_.push(KeyTimeTuple(key, clock_->NowTicks() + lifetime_)); | 40 expiry_queue_.push(KeyTimeTuple(key, clock_->NowTicks() + lifetime_)); |
| 39 while (map_.size() > max_elements_) | 41 while (map_.size() > max_elements_) |
| 40 ClearOldestToken(); | 42 ClearOldestToken(); |
| 41 } | 43 } |
| 42 | 44 |
| 43 bool HasKey(const KeyType& key) { | 45 bool HasKey(const KeyType& key) { |
| 44 ClearExpiredTokens(); | 46 ClearExpiredTokens(); |
| 45 return map_.find(key) != map_.end(); | 47 return map_.find(key) != map_.end(); |
| 46 } | 48 } |
| 47 | 49 |
| 48 const ValueType& GetValue(const KeyType& key) { | 50 const ValueType& GetValue(const KeyType& key) { |
| 49 ClearExpiredTokens(); | 51 ClearExpiredTokens(); |
| 50 typename std::map<KeyType, ValueType>::const_iterator elt = map_.find(key); | 52 typename std::map<KeyType, ValueType>::const_iterator elt = map_.find(key); |
| 51 return elt == map_.end() ? kEmptyValue : elt->second; | 53 return elt == map_.end() ? kEmptyValue : elt->second; |
| 52 } | 54 } |
| 53 | 55 |
| 54 void set_clock_for_testing(base::TickClock* clock) { clock_ = clock; } | 56 // TimedMap takes ownership of this clock. |
| 57 void set_clock_for_testing(base::TickClock* clock) { | |
|
rkc
2014/08/09 06:41:41
Change the clock to a scoped_ptr, pass in a scoped
Charlie
2014/08/09 06:48:23
That's what I wrote first. But then how do you cal
rkc
2014/08/09 06:53:57
Retain a bare pointer in the test. It is the clean
Charlie
2014/08/09 07:10:40
Done.
| |
| 58 DCHECK(clock); | |
| 59 delete clock_; | |
| 60 clock_ = clock; | |
| 61 } | |
| 55 | 62 |
| 56 private: | 63 private: |
| 57 void ClearExpiredTokens() { | 64 void ClearExpiredTokens() { |
| 58 while (!expiry_queue_.empty() && | 65 while (!expiry_queue_.empty() && |
| 59 expiry_queue_.top().second <= clock_->NowTicks()) | 66 expiry_queue_.top().second <= clock_->NowTicks()) |
| 60 ClearOldestToken(); | 67 ClearOldestToken(); |
| 61 } | 68 } |
| 62 | 69 |
| 63 void ClearOldestToken() { | 70 void ClearOldestToken() { |
| 64 map_.erase(expiry_queue_.top().first); | 71 map_.erase(expiry_queue_.top().first); |
| (...skipping 22 matching lines...) Expand all Loading... | |
| 87 std::map<KeyType, ValueType> map_; | 94 std::map<KeyType, ValueType> map_; |
| 88 // Priority queue with our element keys ordered by the earliest expiring keys | 95 // Priority queue with our element keys ordered by the earliest expiring keys |
| 89 // first. | 96 // first. |
| 90 ExpiryQueue expiry_queue_; | 97 ExpiryQueue expiry_queue_; |
| 91 | 98 |
| 92 DISALLOW_COPY_AND_ASSIGN(TimedMap); | 99 DISALLOW_COPY_AND_ASSIGN(TimedMap); |
| 93 }; | 100 }; |
| 94 | 101 |
| 95 } // namespace copresence | 102 } // namespace copresence |
| 96 | 103 |
| 97 #endif // COMPONENTS_COPRESENCE_TIMED_MAP_ | 104 #endif // COMPONENTS_COPRESENCE_TIMED_MAP_H_ |
| OLD | NEW |