1 /*
2  *  Copyright (c) 2016 The WebRTC project authors. All Rights Reserved.
3  *
4  *  Use of this source code is governed by a BSD-style license
5  *  that can be found in the LICENSE file in the root of the source
6  *  tree. An additional intellectual property rights grant can be found
7  *  in the file PATENTS.  All contributing project authors may
8  *  be found in the AUTHORS file in the root of the source tree.
9  */
10 
11 #include "video/quality_threshold.h"
12 
13 #include "test/gtest.h"
14 
15 namespace webrtc {
16 
TEST(QualityThresholdTest,BackAndForth)17 TEST(QualityThresholdTest, BackAndForth) {
18   const int kLowThreshold = 0;
19   const int kHighThreshold = 1;
20   const float kFraction = 0.75f;
21   const int kMaxMeasurements = 10;
22 
23   QualityThreshold thresh(kLowThreshold, kHighThreshold, kFraction,
24                           kMaxMeasurements);
25 
26   const int kNeededMeasurements =
27       static_cast<int>(kFraction * kMaxMeasurements + 1);
28   for (int i = 0; i < kNeededMeasurements; ++i) {
29     EXPECT_FALSE(thresh.IsHigh());
30     thresh.AddMeasurement(kLowThreshold);
31   }
32   ASSERT_TRUE(thresh.IsHigh());
33   for (int i = 0; i < kNeededMeasurements; ++i) {
34     EXPECT_FALSE(*thresh.IsHigh());
35     thresh.AddMeasurement(kHighThreshold);
36   }
37   EXPECT_TRUE(*thresh.IsHigh());
38 
39   for (int i = 0; i < kNeededMeasurements; ++i) {
40     EXPECT_TRUE(*thresh.IsHigh());
41     thresh.AddMeasurement(kLowThreshold);
42   }
43   EXPECT_FALSE(*thresh.IsHigh());
44 }
45 
TEST(QualityThresholdTest,Variance)46 TEST(QualityThresholdTest, Variance) {
47   const int kLowThreshold = 0;
48   const int kHighThreshold = 1;
49   const float kFraction = 0.8f;
50   const int kMaxMeasurements = 10;
51   const double kMaxError = 0.01;
52 
53   // Previously randomly generated values...
54   int values[] = {51, 79, 80, 56, 19, 20, 48, 57, 48, 25, 2, 25, 38, 37, 25};
55   // ...with precomputed variances.
56   double variances[] = {476.9, 687.6, 552, 336.4, 278.767, 265.167};
57 
58   QualityThreshold thresh(kLowThreshold, kHighThreshold, kFraction,
59                           kMaxMeasurements);
60 
61   for (int i = 0; i < kMaxMeasurements; ++i) {
62     EXPECT_FALSE(thresh.CalculateVariance());
63     thresh.AddMeasurement(values[i]);
64   }
65 
66   ASSERT_TRUE(thresh.CalculateVariance());
67   EXPECT_NEAR(variances[0], *thresh.CalculateVariance(), kMaxError);
68   for (unsigned int i = 1; i < sizeof(variances) / sizeof(double); ++i) {
69     thresh.AddMeasurement(values[i + kMaxMeasurements - 1]);
70     EXPECT_NEAR(variances[i], *thresh.CalculateVariance(), kMaxError);
71   }
72 
73   for (int i = 0; i < kMaxMeasurements; ++i) {
74     thresh.AddMeasurement(42);
75   }
76   EXPECT_NEAR(0, *thresh.CalculateVariance(), kMaxError);
77 }
78 
TEST(QualityThresholdTest,BetweenThresholds)79 TEST(QualityThresholdTest, BetweenThresholds) {
80   const int kLowThreshold = 0;
81   const int kHighThreshold = 2;
82   const float kFraction = 0.6f;
83   const int kMaxMeasurements = 10;
84 
85   const int kBetweenThresholds = (kLowThreshold + kHighThreshold) / 2;
86 
87   QualityThreshold thresh(kLowThreshold, kHighThreshold, kFraction,
88                           kMaxMeasurements);
89 
90   for (int i = 0; i < 2 * kMaxMeasurements; ++i) {
91     EXPECT_FALSE(thresh.IsHigh());
92     thresh.AddMeasurement(kBetweenThresholds);
93   }
94   EXPECT_FALSE(thresh.IsHigh());
95 }
96 
TEST(QualityThresholdTest,FractionHigh)97 TEST(QualityThresholdTest, FractionHigh) {
98   const int kLowThreshold = 0;
99   const int kHighThreshold = 2;
100   const float kFraction = 0.75f;
101   const int kMaxMeasurements = 10;
102 
103   const int kBetweenThresholds = (kLowThreshold + kHighThreshold) / 2;
104   const int kNeededMeasurements =
105       static_cast<int>(kFraction * kMaxMeasurements + 1);
106 
107   QualityThreshold thresh(kLowThreshold, kHighThreshold, kFraction,
108                           kMaxMeasurements);
109 
110   for (int i = 0; i < kMaxMeasurements; ++i) {
111     EXPECT_FALSE(thresh.FractionHigh(1));
112     thresh.AddMeasurement(kBetweenThresholds);
113   }
114 
115   for (int i = 0; i < kNeededMeasurements; i++) {
116     EXPECT_FALSE(thresh.FractionHigh(1));
117     thresh.AddMeasurement(kHighThreshold);
118   }
119   EXPECT_FALSE(thresh.FractionHigh(2));
120   ASSERT_TRUE(thresh.FractionHigh(1));
121   EXPECT_NEAR(*thresh.FractionHigh(1), 1, 0.001);
122 
123   for (int i = 0; i < kNeededMeasurements; i++) {
124     EXPECT_NEAR(*thresh.FractionHigh(1), 1, 0.001);
125     thresh.AddMeasurement(kLowThreshold);
126   }
127   EXPECT_NEAR(
128       *thresh.FractionHigh(1),
129       static_cast<double>(kNeededMeasurements) / (kNeededMeasurements + 1),
130       0.001);
131 }
132 
133 }  // namespace webrtc
134