OLD | NEW |
---|---|
1 // Copyright 2016 The Chromium Authors. All rights reserved. | 1 // Copyright 2016 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 NET_NQE_OBSERVATION_BUFFER_H_ | 5 #ifndef NET_NQE_OBSERVATION_BUFFER_H_ |
6 #define NET_NQE_OBSERVATION_BUFFER_H_ | 6 #define NET_NQE_OBSERVATION_BUFFER_H_ |
7 | 7 |
8 #include <float.h> | 8 #include <float.h> |
9 | 9 |
10 #include <algorithm> | 10 #include <algorithm> |
11 #include <deque> | 11 #include <deque> |
12 #include <memory> | |
12 #include <vector> | 13 #include <vector> |
13 | 14 |
14 #include "base/gtest_prod_util.h" | |
15 #include "base/macros.h" | 15 #include "base/macros.h" |
16 #include "base/time/default_tick_clock.h" | |
RyanSturm
2016/09/26 18:44:55
This pulls in base/time/tick_clock.h, but you shou
tbansal1
2016/09/28 16:42:31
Done.
| |
16 #include "base/time/time.h" | 17 #include "base/time/time.h" |
17 #include "net/base/net_export.h" | 18 #include "net/base/net_export.h" |
19 #include "net/nqe/network_quality_observation.h" | |
RyanSturm
2016/09/26 18:44:55
Is network_quality_observation.h needed?
tbansal1
2016/09/28 16:42:31
Yes. See Line 174:
std::deque<Observation<ValueTyp
| |
18 #include "net/nqe/network_quality_observation_source.h" | 20 #include "net/nqe/network_quality_observation_source.h" |
19 #include "net/nqe/weighted_observation.h" | 21 #include "net/nqe/weighted_observation.h" |
20 | 22 |
21 namespace net { | 23 namespace net { |
22 | 24 |
23 namespace nqe { | 25 namespace nqe { |
24 | 26 |
25 namespace internal { | 27 namespace internal { |
26 | 28 |
27 // Stores observations sorted by time. | 29 // Stores observations sorted by time. |
28 template <typename ValueType> | 30 template <typename ValueType> |
29 class NET_EXPORT_PRIVATE ObservationBuffer { | 31 class NET_EXPORT_PRIVATE ObservationBuffer { |
30 public: | 32 public: |
31 explicit ObservationBuffer(double weight_multiplier_per_second) | 33 explicit ObservationBuffer(double weight_multiplier_per_second) |
32 : weight_multiplier_per_second_(weight_multiplier_per_second) { | 34 : weight_multiplier_per_second_(weight_multiplier_per_second), |
35 tick_clock_(new base::DefaultTickClock()) { | |
33 static_assert(kMaximumObservationsBufferSize > 0U, | 36 static_assert(kMaximumObservationsBufferSize > 0U, |
34 "Minimum size of observation buffer must be > 0"); | 37 "Minimum size of observation buffer must be > 0"); |
35 DCHECK_GE(weight_multiplier_per_second_, 0.0); | 38 DCHECK_GE(weight_multiplier_per_second_, 0.0); |
36 DCHECK_LE(weight_multiplier_per_second_, 1.0); | 39 DCHECK_LE(weight_multiplier_per_second_, 1.0); |
37 } | 40 } |
38 | 41 |
39 ~ObservationBuffer() {} | 42 ~ObservationBuffer() {} |
40 | 43 |
41 // Adds |observation| to the buffer. The oldest observation in the buffer | 44 // Adds |observation| to the buffer. The oldest observation in the buffer |
42 // will be evicted to make room if the buffer is already full. | 45 // will be evicted to make room if the buffer is already full. |
(...skipping 21 matching lines...) Expand all Loading... | |
64 void Clear() { observations_.clear(); } | 67 void Clear() { observations_.clear(); } |
65 | 68 |
66 // Returns true iff the |percentile| value of the observations in this | 69 // Returns true iff the |percentile| value of the observations in this |
67 // buffer is available. Sets |result| to the computed |percentile| | 70 // buffer is available. Sets |result| to the computed |percentile| |
68 // value among all observations since |begin_timestamp|. If the value is | 71 // value among all observations since |begin_timestamp|. If the value is |
69 // unavailable, false is returned and |result| is not modified. Percentile | 72 // unavailable, false is returned and |result| is not modified. Percentile |
70 // value is unavailable if all the values in observation buffer are older | 73 // value is unavailable if all the values in observation buffer are older |
71 // than |begin_timestamp|. | 74 // than |begin_timestamp|. |
72 // |result| must not be null. | 75 // |result| must not be null. |
73 bool GetPercentile(const base::TimeTicks& begin_timestamp, | 76 bool GetPercentile(const base::TimeTicks& begin_timestamp, |
74 ValueType* result, | 77 ValueType* result, |
RyanSturm
2016/09/26 18:44:55
nit: Would you mind moving result to be the last p
tbansal1
2016/09/28 16:42:31
Added TODO.
| |
75 int percentile, | 78 int percentile, |
76 const std::vector<NetworkQualityObservationSource>& | 79 const std::vector<NetworkQualityObservationSource>& |
77 disallowed_observation_sources) const { | 80 disallowed_observation_sources) const { |
78 DCHECK(result); | 81 DCHECK(result); |
79 DCHECK_GE(Capacity(), Size()); | 82 DCHECK_GE(Capacity(), Size()); |
80 // Stores WeightedObservation in increasing order of value. | 83 // Stores WeightedObservation in increasing order of value. |
81 std::vector<WeightedObservation<ValueType>> weighted_observations; | 84 std::vector<WeightedObservation<ValueType>> weighted_observations; |
82 | 85 |
83 // Total weight of all observations in |weighted_observations|. | 86 // Total weight of all observations in |weighted_observations|. |
84 double total_weight = 0.0; | 87 double total_weight = 0.0; |
(...skipping 24 matching lines...) Expand all Loading... | |
109 | 112 |
110 // Computation may reach here due to floating point errors. This may happen | 113 // Computation may reach here due to floating point errors. This may happen |
111 // if |percentile| was 100 (or close to 100), and |desired_weight| was | 114 // if |percentile| was 100 (or close to 100), and |desired_weight| was |
112 // slightly larger than |total_weight| (due to floating point errors). | 115 // slightly larger than |total_weight| (due to floating point errors). |
113 // In this case, we return the highest |value| among all observations. | 116 // In this case, we return the highest |value| among all observations. |
114 // This is same as value of the last observation in the sorted vector. | 117 // This is same as value of the last observation in the sorted vector. |
115 *result = weighted_observations.at(weighted_observations.size() - 1).value; | 118 *result = weighted_observations.at(weighted_observations.size() - 1).value; |
116 return true; | 119 return true; |
117 } | 120 } |
118 | 121 |
122 void SetTickClockForTesting(std::unique_ptr<base::TickClock> tick_clock) { | |
RyanSturm
2016/09/26 18:44:55
nit: Maybe add tick_clock as a parameter to the co
tbansal1
2016/09/28 16:42:31
Seems like net tends to use ForTesting() rather th
| |
123 tick_clock_ = std::move(tick_clock); | |
124 } | |
125 | |
119 private: | 126 private: |
120 // Maximum number of observations that can be held in the ObservationBuffer. | 127 // Maximum number of observations that can be held in the ObservationBuffer. |
121 static const size_t kMaximumObservationsBufferSize = 300; | 128 static const size_t kMaximumObservationsBufferSize = 300; |
122 | 129 |
123 // Computes the weighted observations and stores them in | 130 // Computes the weighted observations and stores them in |
124 // |weighted_observations| sorted by ascending |WeightedObservation.value|. | 131 // |weighted_observations| sorted by ascending |WeightedObservation.value|. |
125 // Only the observations with timestamp later than |begin_timestamp| are | 132 // Only the observations with timestamp later than |begin_timestamp| are |
126 // considered. Also, sets |total_weight| to the total weight of all | 133 // considered. Also, sets |total_weight| to the total weight of all |
127 // observations. Should be called only when there is at least one | 134 // observations. Should be called only when there is at least one |
128 // observation in the buffer. | 135 // observation in the buffer. |
129 void ComputeWeightedObservations( | 136 void ComputeWeightedObservations( |
130 const base::TimeTicks& begin_timestamp, | 137 const base::TimeTicks& begin_timestamp, |
131 std::vector<WeightedObservation<ValueType>>& weighted_observations, | 138 std::vector<WeightedObservation<ValueType>>& weighted_observations, |
132 double* total_weight, | 139 double* total_weight, |
133 const std::vector<NetworkQualityObservationSource>& | 140 const std::vector<NetworkQualityObservationSource>& |
134 disallowed_observation_sources) const { | 141 disallowed_observation_sources) const { |
135 DCHECK_GE(Capacity(), Size()); | 142 DCHECK_GE(Capacity(), Size()); |
136 | 143 |
137 weighted_observations.clear(); | 144 weighted_observations.clear(); |
138 double total_weight_observations = 0.0; | 145 double total_weight_observations = 0.0; |
139 base::TimeTicks now = base::TimeTicks::Now(); | 146 base::TimeTicks now = tick_clock_->NowTicks(); |
140 | 147 |
141 for (const auto& observation : observations_) { | 148 for (const auto& observation : observations_) { |
142 if (observation.timestamp < begin_timestamp) | 149 if (observation.timestamp < begin_timestamp) |
143 continue; | 150 continue; |
144 bool disallowed = false; | 151 bool disallowed = false; |
145 for (const auto& disallowed_source : disallowed_observation_sources) { | 152 for (const auto& disallowed_source : disallowed_observation_sources) { |
146 if (disallowed_source == observation.source) | 153 if (disallowed_source == observation.source) |
147 disallowed = true; | 154 disallowed = true; |
148 } | 155 } |
149 if (disallowed) | 156 if (disallowed) |
(...skipping 17 matching lines...) Expand all Loading... | |
167 // front of the queue. | 174 // front of the queue. |
168 std::deque<Observation<ValueType>> observations_; | 175 std::deque<Observation<ValueType>> observations_; |
169 | 176 |
170 // The factor by which the weight of an observation reduces every second. | 177 // The factor by which the weight of an observation reduces every second. |
171 // For example, if an observation is 6 seconds old, its weight would be: | 178 // For example, if an observation is 6 seconds old, its weight would be: |
172 // weight_multiplier_per_second_ ^ 6 | 179 // weight_multiplier_per_second_ ^ 6 |
173 // Calculated from |kHalfLifeSeconds| by solving the following equation: | 180 // Calculated from |kHalfLifeSeconds| by solving the following equation: |
174 // weight_multiplier_per_second_ ^ kHalfLifeSeconds = 0.5 | 181 // weight_multiplier_per_second_ ^ kHalfLifeSeconds = 0.5 |
175 const double weight_multiplier_per_second_; | 182 const double weight_multiplier_per_second_; |
176 | 183 |
184 std::unique_ptr<base::TickClock> tick_clock_; | |
185 | |
177 DISALLOW_COPY_AND_ASSIGN(ObservationBuffer); | 186 DISALLOW_COPY_AND_ASSIGN(ObservationBuffer); |
178 }; | 187 }; |
179 | 188 |
180 } // namespace internal | 189 } // namespace internal |
181 | 190 |
182 } // namespace nqe | 191 } // namespace nqe |
183 | 192 |
184 } // namespace net | 193 } // namespace net |
185 | 194 |
186 #endif // NET_NQE_OBSERVATION_BUFFER_H_ | 195 #endif // NET_NQE_OBSERVATION_BUFFER_H_ |
OLD | NEW |