C# 新元素优化的RSI计算

C# 新元素优化的RSI计算,c#,C#,以下公式将计算所有价格的RSI。每当我向数组中添加新价格时,它都必须重新计算整个数组/所有价格的RSI。有没有一种方法可以计算新价格的RSI,而不必重新计算整个价格?我想这样做是因为当我计算每一根新蜡烛的能量时,它必须在尽可能短的时间内执行。如果这是不可能的,你能建议我一种方法来优化它,使它尽可能快地执行。现在,没那么快 decimal[] prices = ... Calculate(prices, 14); public decimal[]计算(decimal[]价格,整数周期) { va

以下公式将计算所有价格的RSI。每当我向数组中添加新价格时,它都必须重新计算整个数组/所有价格的RSI。有没有一种方法可以计算新价格的RSI,而不必重新计算整个价格?我想这样做是因为当我计算每一根新蜡烛的能量时,它必须在尽可能短的时间内执行。如果这是不可能的,你能建议我一种方法来优化它,使它尽可能快地执行。现在,没那么快

decimal[] prices = ...
Calculate(prices, 14);
public decimal[]计算(decimal[]价格,整数周期)
{
var rsi=新的小数点[价格.长度];
十进制增益=0m;
十进制损耗=0m;
rsi[0]=0m;
对于(int i=1;i=0)
{
增益+=diff;
}
其他的
{
损失-=差异;
}
}
十进制avrg=增益/周期;
十进制avrl=损失/期间;
十进制rs=增益/损耗;
rsi[周期]=100m-(100m/(1m+rs));
对于(int i=期间+1;i<价格长度;++i)
{
var diff=价格[i]-价格[i-1];
如果(差异>=0)
{
avrg=((avrg*(周期-1))+diff)/周期;
avrl=(avrl*(时段-1))/时段;
}
其他的
{
avrl=((avrl*(期间-1))-diff)/期间;
avrg=(avrg*(周期-1))/周期;
}
rs=avrg/avrl;
rsi[i]=100m-(100m/(1m+rs));
}
回归rsi;
}

如果保留项目数和项目总数,然后再添加一个,则无需计算总和。新和是旧和+新值。那么平均值是新的和/N+1。@jdweng,您想键入它作为答案吗?此外,我所拥有的是包含所有价格的
decimal[]price
。但是我可以保存
增益
损失
public decimal[] Calculate(decimal[] price, int period)
{
    var rsi = new decimal[price.Length];

    decimal gain = 0m;
    decimal loss = 0m;

    rsi[0] = 0m;

    for (int i = 1; i <= period; ++i)
    {
        var diff = price[i] - price[i - 1];
        if (diff >= 0)
        {
            gain += diff;
        }
        else
        {
            loss -= diff;
        }
    }

    decimal avrg = gain / period;
    decimal avrl = loss / period;
    decimal rs = gain / loss;
    rsi[period] = 100m - (100m / (1m + rs));

    for (int i = period + 1; i < price.Length; ++i)
    {
        var diff = price[i] - price[i - 1];

        if (diff >= 0)
        {
            avrg = ((avrg * (period - 1)) + diff) / period;
            avrl = (avrl * (period - 1)) / period;
        }
        else
        {
            avrl = ((avrl * (period - 1)) - diff) / period;
            avrg = (avrg * (period - 1)) / period;
        }

        rs = avrg / avrl;

        rsi[i] = 100m - (100m / (1m + rs));
    }

    return rsi;
}