如何使用R计算微软(MSFT)收盘价SMA、制定交易策略并绘制图表
代码问题排查
首先你的代码存在两个核心问题:
- 你要获取微软的行情,但是
getSymbols里填的ticker是MCD(麦当劳的代码),需要修改为MSFT - 你写的第一个
fx函数只能返回最新n日的SMA单值,无法生成全历史交易日对应的SMA序列,没法满足绘图需求;第二个smafn逻辑是正确的,不过不需要重复造轮子,quantmod包已经封装了高效的SMA()计算函数
实现步骤
1. 数据获取
使用修正后的代码获取微软上市至今的行情数据,保留原生xts格式方便后续指标计算和绘图,不推荐使用attach()函数,避免变量名冲突。
2. 均线计算
直接调用quantmod内置的SMA()函数分别计算20日、50日均线,也可以用你自己写的smafn验证计算结果,两者输出完全一致。
3. 信号生成
按你的策略逻辑生成交易信号:20日均线上穿50日均线时为买入信号,反之为卖出信号。
4. 可视化绘图
可以直接用quantmod自带的金融绘图函数快速生成带均线的K线图,也可以用ggplot2自定义绘制折线对比图。
完整可运行代码
library(quantmod) # 获取1986年3月13日至今的微软(MSFT)行情数据 msftData <- getSymbols("MSFT", src = "yahoo", from = "1986-03-13", auto.assign = FALSE) # 重命名列方便调用 colnames(msftData) <- c("Open","High","Low","Close","Volume","Adjusted") # 计算20日、50日简单移动平均线 sma20 <- SMA(msftData$Close, n = 20) sma50 <- SMA(msftData$Close, n = 50) # (可选)验证你写的smafn函数计算结果和官方函数一致 smafn <- function(price, n=1){ cx <- c(0, cumsum(ifelse(is.na(price), 0, price))) cn <- c(0, cumsum(ifelse(is.na(price), 0, 1))) rx <- cx[(n+1):length(cx)] - cx[1:(length(cx) - n)] rn <- cn[(n+1):length(cn)] - cn[1:(length(cn) - n)] rsum <- rx / rn # 前n-1个值补NA对齐原序列长度 return(c(rep(NA, n-1), rsum)) } sma20_self <- smafn(msftData$Close, n=20) sma50_self <- smafn(msftData$Close, n=50) # 生成交易信号 trade_signal <- ifelse(sma20 > sma50, "买入", "卖出") # 方法1:用quantmod自带函数快速绘制K线+均线图,subset参数控制展示的时间段,示例为2021年至今 chartSeries(msftData, subset = "2021::", name = "MSFT 收盘价与均线走势", TA = c(addSMA(n=20, col="blue"), addSMA(n=50, col="red"))) # 蓝色为20日均线,红色为50日均线,蓝色上穿红色触发买入信号,下穿触发卖出信号
如果需要自定义折线对比图,可以用ggplot2实现:
library(ggplot2) # 转换为数据框格式 plot_data <- data.frame( date = index(msftData), close = as.numeric(msftData$Close), sma20 = as.numeric(sma20), sma50 = as.numeric(sma50) ) # 取近3年数据绘图 plot_data_recent <- subset(plot_data, date >= as.Date("2021-01-01")) ggplot(plot_data_recent, aes(x = date)) + geom_line(aes(y = close, color = "收盘价"), linewidth = 0.5) + geom_line(aes(y = sma20, color = "20日均线"), linewidth = 0.8) + geom_line(aes(y = sma50, color = "50日均线"), linewidth = 0.8) + labs(title = "微软(MSFT)收盘价与均线走势", x = "日期", y = "价格(美元)", color = "指标") + scale_color_manual(values = c("收盘价" = "black", "20日均线" = "blue", "50日均线" = "red")) + theme_minimal()
内容的提问来源于stack exchange,提问作者itchy cat
相关产品推荐
相关产品推荐

