我正在使用Google表格和GoogleFinance函数来获取库存数据。我可以使用以下公式计算一个简单的移动平均线。我正在尝试为每种股票获取长度为8,13,21,55的指数移动平均线。关于指数移动平均线公式的任何建议
=AVERAGE(INDEX(GoogleFinance("MSFT","all",WORKDAY(TODAY(),-8),TODAY()),,3))
答案 0 :(得分:2)
我发现this已归功于该用户“ Jonathan K 2806”。
尝试一下,更简单,也许足够:
/**
* Calculates the EMA of the range.
*
* @param {range} range The range of cells to calculate.
* @param {number} n The number of trailing samples to give higer weight to, e.g. 30.
* @return The EMA of the range.
* @customfunction
*/
function EMA(range, n) {
if (!range.reduce) {
return range;
}
n = Math.min(n, range.length);
var a = 2 / (n + 1);
return range.reduce(function(accumulator, currentValue, index, array) {
return currentValue != "" ? (currentValue * a + accumulator * (1-a)) : accumulator;
}, 0);
}
转到工具->脚本编辑器,将其粘贴并点击保存,然后返回到电子表格并在单元格= EMA($ A2:$ A100,10)中键入,或者您想使用它。< / p>
答案 1 :(得分:2)
以下公式用于计算当前的指数移动平均线(EMA):
EMA =收盘价x衰落_多玩家+ EMA(前一天)x (1-decay_multiplayer)
EMA对近期价格给予较高的权重,而常规移动平均线对所有值赋予相同的权重。
应选择 decay_multiplayer 。
如果您选择一个较大的数字,如短期移动平均线(更快的衰减),而您选择较小的数字,如长期移动平均线。
要在Google工作表中实施此操作,您必须创建一个新列来代表每天的EMV值。您必须填写第一个EMV值(带有第一个收盘价),然后使用上面的函数从当前收盘价和以前的EMV值计算每个新的EMV。
我在这里创建了一个Google工作表作为示例: https://docs.google.com/spreadsheets/d/1ITfRfwQCBV-0amWpZzae2PbKBPAL_8YluUEmU_vbsCI/edit?usp=sharing
答案 2 :(得分:2)
回馈对 Jonathan K 工作的一些改进。
提高短输入的准确性(range.length = 1 或 2)
边界检查 n
指定输入数组的预期顺序
给出 1 个替代定义
添加测试功能
/**
* Calculates the EMA of the range.
*
* @param {range} range The range of cells to calculate. New values (higher weight) should be on the left.
* @param {number} n The number of trailing samples to give higher weight to, e.g. 30.
* Values below 1 are treated as 1, which will just return the most recent value.
* @return The EMA of the range.
* @customfunction
*/
function EMA(range, n) {
if (!range.reduce) {
// can't run ema - bail
return range;
} else if (range.flat && range.reverse) {
// flatten the array if possible & reorganize w/ new values on right (last)
// NOTE: remove .reverse if the rightmost elements of input range are most recent / need higher weight
range = range.flat().reverse();
}
n = Math.max(n,1); // n has lower bound of 1
var a = 1-(2/(n+1));
// with the existing a setup, 86% of the total EMA weight will belong to the first n values.
// an alternate definition for a where n would be the desired number of intervals to keep (?)
// ex: n = 4 -> quarterly values would get a "mean lifetime" of 1 year.
// var a = 1-Math.exp(-1 / n);
return range.reduce(function(accumulator, currentValue, index, array) {
if (currentValue != "") {
if (accumulator == null) {
return currentValue;
} else {
return currentValue * a + accumulator * (1-a);
}
} else {
return accumulator;
}
}, null);
}
function test() {
var emaValue = EMA([[13,14],[15,16]], 4);
Logger.log(emaValue);
}
答案 3 :(得分:1)
以上公式在技术上与指数移动平均线不同。 指数衰减函数如下。 https://en.wikipedia.org/wiki/Exponential_decay
通常用于对随着时间的推移而衰减的影响进行建模,其中更重的是权重更接近的条目(如上所述)。话虽如此,上式并不相同。
EWMA / EMA的实际形式有些不同,可以在这里找到:https://en.wikipedia.org/wiki/Moving_average#Exponential_moving_average
以上可能被认为是指数平滑的一种变体,但实际上并非如此:https://en.wikipedia.org/wiki/Exponential_smoothing
就个人而言,我更喜欢使用e ^ -ax函数加权平均值。我可以控制“ a”参数来设置较早和较晚项目的权重,以更好地调整权重。
currentValueComponent_i = currentValue * e ^ -time_i / Tau 为所需的任何项目添加尽可能多的currentValueComponents。 Tau是指将63%的元素衰减的时间常数,这些元素将添加到每次迭代中,具体取决于加权平均值中包含的项目数。
资料来源:我是一名工程师。我会定期这样做。
答案 4 :(得分:1)
最简单的方法是,给定列X2:X...
和单元格Z1
中的权重系数a,可以递归计算行Y2:Y...
中的指数移动平均值如下:< /p>
EMA
=X2
=$Z$1*X3+(1-$Z$1)*(Y2)
=$Z$1*X4+(1-$Z$1)*(Y3)
=$Z$1*X5+(1-$Z$1)*(Y4)
=... # the pattern will repeat itself properly using the drag function
这里描述了递归公式: https://en.wikipedia.org/wiki/Moving_average#Exponential_moving_average
当然,这仅适用于数据点之间的间隔始终相同的情况。