28. 計算移動平均值函數


一. 定義

1.移動平均值是什么?

(1)移動平均值,是一種統計指標,用於觀測一組隨時間變化的量。

(2)M-移動平均值,是最后 M 個數的移動平均值。一定要注意,這邊算出的平均值是一組數,而不是一個數。

2. 移動平均值怎么算?

首先我們給出一組數據,data = ( 1, 2, 3, 4, 5, 6 ),現在我們需要計算 M = 3 時的移動平均值。那么第一個移動平均值就是(1, 2, 3)的算術平均值,第二個移動平均值就是(2, 3, 4)的算術平均值,其余同理。

3. 移動平均值的作用是什么?

給定一組數據,這組數據應該是隨時間變化記錄得到的,它可以是某商品一年的銷量,也可以是你一年考試的成績。通過計算這組數據的移動平均值,我們可以簡單預測未來的表現。

二. 代碼實現

1.函數代碼

 1 vector<double> moving_average(const vector<int>& data, int m) {
 2     vector<double> m_averages;
 3 
 4     for (int i = m - 1; i < data.size(); ++i) {
 5         double current_sum = 0.0;
 6 
 7         for (int j = i - m + 1; j <= i; ++j) {
 8             current_sum += data[j];
 9         }
10         double avg = current_sum / m;
11         m_averages.push_back(avg);
12     }
13 
14     return m_averages;
15 }

2.算法分析

我們來分析一下這段代碼。首先,函數傳入一個需要處理的數據列,並且需要一個 M ,來告訴我們將會處理幾個數的平均值。前面提到,移動平均值實際上是一組數,所以函數也應該返回一組數:這里返回一個 vector。

外層循環控制整體范圍,我們希望它的下標不要超過數據的數量。每次計算 M 個數的平均值,所以應該從 M - 1 開始(如果從 M 位置開始,那么最后一個數字將不能被計算到,也就是說,返回的平均值里面,會丟掉最后一次的計算)。

內層循環控制小的范圍,每次只累加固定 M 個數的部分和。在每次計算完成后,我們將當前的平均值加入到平均值組中。

不難看出,下標的開始與結束,非常復雜,不容易理解,並且算法的時間復雜度是 O(n^2),這個復雜度對於小型數據組可以接受,但是處理大型數據組的時候,難免顯得力不從心。

當一件事情的解決方式並不優雅的時候,一般來說都會出錯,那么我們來優化算法。

3. 優化

通過上述分析,我們得知,很多功夫都花費在計算部分和上,而這個部分和很大一部分是不變的,每次變化的,只是第一個數據和最后一個數據。立即推,我們對於重復部分不進行重復計算。優化后的代碼如下:

 1 vector<double> moving_average(const vector<int>& data, int m) {
 2     vector<double> m_averages;
 3     double current_sum = 0.0;
 4 
 5     for (int i = 0; i < m - 1; ++i) {
 6         current_sum += data[i];
 7     }
 8 
 9     for (int i = m - 1; i < data.size(); ++i) {
10         current_sum += data[i];
11         double avg = current_sum / m;
12         m_averages.push_back(avg);
13         current_sum -= data[i - m + 1];
14     }
15     
16     return m_averages;
17 }

現在再來分析一下優化后的新函數。

第一個循環計算 M - 1 個部分和,這個部分和其實是缺失的,因為少了最后一個數據,但是它開啟了后續的步驟。在第二個循環中,我們先把缺失的數據加進去,然后計算平均值,接着將平均值放到平均值組里,再將最前面的一個元素,從部分和中減去,這樣就為下一次循環做好了准備。新函數的時間復雜度是 O(n),應對大型數據的時候,效果也很不錯。

 


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM