[英]std::deque memory use
我已經實現了一個簡單的統計引擎,使用雙端隊列返回滾動均值和方差,以提供數據隊列。
雙端隊列由與滾動值數量相等的條目數構成。
當一個新值到達時,最舊的值會從前面彈出,新的值會被推到后面。
我需要確保這不會在 memory 中增長,因為它預計會作為后台任務運行很長時間。
雙端隊列是否在使用中的堆上分配? 有沒有可以用來修復其大小的標志?
我在 RHEL 5.3 上使用 G++ 4.1.2
本質上,任何動態大小的容器都會從堆中分配 memory。 另一個問題概述了 deque 的實現。
但是在您的特定情況下,隊列始終具有相同的大小。 如果遇到雙端隊列問題,使用固定大小數組上的循環緩沖區實現簡單的固定大小隊列可能會有所幫助。 此實現應該具有從根本上更好的 memory 行為(因為它從不需要重新分配)。 如果不分析數據,很難評估其優勢是否值得實施。
就像提示一樣,如果您不需要跟蹤值,那么這個很棒的算法非常輕量級(我什至在 8bit micros 上使用它)並且是准確的。
class RunningStat
{
public:
RunningStat() : m_n(0) {}
void Clear()
{
m_n = 0;
}
void Push(double x)
{
m_n++;
// See Knuth TAOCP vol 2, 3rd edition, page 232
if (m_n == 1)
{
m_oldM = m_newM = x;
m_oldS = 0.0;
}
else
{
m_newM = m_oldM + (x - m_oldM)/m_n;
m_newS = m_oldS + (x - m_oldM)*(x - m_newM);
// set up for next iteration
m_oldM = m_newM;
m_oldS = m_newS;
}
}
int NumDataValues() const
{
return m_n;
}
double Mean() const
{
return (m_n > 0) ? m_newM : 0.0;
}
double Variance() const
{
return ( (m_n > 1) ? m_newS/(m_n - 1) : 0.0 );
}
double StandardDeviation() const
{
return sqrt( Variance() );
}
private:
int m_n;
double m_oldM, m_newM, m_oldS, m_newS;
};
該算法由 BP Welford 創建,並在 Donald Knuth 的計算機編程藝術,第 2 卷,第 232 頁,第 3 版中介紹。
該規范將實現細節留給供應商。 但是,由於兩端的插入是有效的,因此很可能將其實現為堆上的鏈接結構。 話雖如此,當您從堆中彈出某些東西時,它應該被解構,因此您的總 memory 使用量不應攀升。
聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.