本文最新版已更新至http://thinkinside.tk/2013/05/03/r_notes_1_what.html


在學(xué)習(xí)量化投資的時候,我發(fā)現(xiàn)了R(www.r-project.org)。R到底是什么呢?在開始之前,先看看R的神奇之處。
1. R初窺
從CRAN(The Comprehensive R Archive Network)cran.r-project.org—mirrors.html中選擇一個鏡像,然后下載合適的安裝包(R支持Linux、Mac OS X和Windows)。
安裝并運(yùn)行R后,可以看到R的控制臺(我的操作系統(tǒng)是Mac OS):

在R的控制臺輸入如下命令:
> install.packages('quantmod') # 安裝quantmod包
> require(quantmod) #引用quantmod包
> getSymbols("GOOG",src="yahoo",from="2013-01-01", to='2013-04-24') #從雅虎財(cái)經(jīng)獲取google的股票數(shù)據(jù)
> chartSeries(GOOG,up.col='red',dn.col='green') #顯示K線圖
> addMACD() #增加MACD圖
就能夠看到下圖的效果了:

最后,退出R:
> q()#Terminate an R Session
2. R是什么
是不是很神奇?反正當(dāng)時我完全被Hold住了。
那么R到底是什么?或者說,R到底是做什么用的?從不同的角度出發(fā),對R會有不同的描述。
- 從使用角度,R是一個有著統(tǒng)計(jì)分析功能及強(qiáng)大作圖功能的軟件,在GNU協(xié)議General Public Licence4下免費(fèi)發(fā)行。
- 從編程角度,R語言是面向?qū)ο蟮慕y(tǒng)計(jì)編程語言,是由AT&T貝爾實(shí)驗(yàn)室所創(chuàng)的S語言發(fā)展出的一種方言。
- 從計(jì)算角度,R 是一種為統(tǒng)計(jì)計(jì)算和圖形顯示而設(shè)計(jì)的語言及環(huán)境。
- 從開發(fā)角度,R 是一組開源的數(shù)據(jù)操作,計(jì)算和圖形顯示工具的整合包有各種方式可以進(jìn)行編程調(diào)用。
- 從架構(gòu)角度,R 是為統(tǒng)計(jì)計(jì)算和圖形展示而設(shè)計(jì)的一個系統(tǒng)。它包括一種編程語言,高級別圖形展示函數(shù),和其它語言的接口以及調(diào)試工具。
如果一定要找到一個與R類似的軟件,那就是商業(yè)軟件Matlab。R和Matlab都是基于編程進(jìn)行數(shù)據(jù)分析的工具,Matlab適用的領(lǐng)域更廣,而R更擅長統(tǒng)計(jì)分析領(lǐng)域。
與Matlab相比,R更具備開放性:
- R是自由軟件,Matlab是商業(yè)軟件;
- R可以方便的通過“包”進(jìn)行擴(kuò)展,R的核心只有25個包,但是有幾千個外部包可以調(diào)用,當(dāng)然你也可以開發(fā)自己的;
- R語言比Matlab的要強(qiáng)大;
- R和其他編程語言/數(shù)據(jù)庫之間有很好的接口;其他語言也可以很方便的調(diào)用R的API和結(jié)果對象。
R常用于金融和統(tǒng)計(jì)領(lǐng)域。大多數(shù)人使用R就是因?yàn)樗慕y(tǒng)計(jì)功能,R的內(nèi)部實(shí)現(xiàn)了很多經(jīng)典的or時髦的統(tǒng)計(jì)技術(shù)。

3. R的核心概念
3.1 對象
R語言是一種面向?qū)ο蟮恼Z言,所有的對象都有兩個內(nèi)在屬性:元素類型和長度。
元素類型是對象內(nèi)元素的基本類型,包括:數(shù)值(numeric),字符型(character),復(fù)數(shù)型(complex)、邏輯型(logical)、函數(shù)(function)等,通過mode()函數(shù)可以查看一個對象的類型。
長度是對象中元素的數(shù)目,通過函數(shù)length()可以查看對象的長度。
除了元素類型外,對象本身也有不同的“類型”,表示不同的數(shù)據(jù)結(jié)構(gòu)(struct)。R中的對象類型主要包括:
向量(vector): 由一系列有序元素構(gòu)成。
因子(factor):對同長的其他向量元素進(jìn)行分類(分組)的向量對象。R 同時提供有序(ordered)和無序(unordered)因子。
數(shù)組(array):帶有多個下標(biāo)的類型相同的元素的集合
矩陣(matrix):矩陣僅僅是一個雙下標(biāo)的數(shù)組。R提供了一下函數(shù)專門處理二維數(shù)組(矩陣)。
數(shù)據(jù)框(data frame):和矩陣類似的一種結(jié)構(gòu)。在數(shù)據(jù)框中,列可以是不同的對象。
時間序列(time series):包含一些額外的屬性,如頻率和時間.
列表(list):是一種泛化(general form)的向量。它沒有要求所有元素是同一類型,許多時候就是向量和列表類型。列表為統(tǒng)計(jì)計(jì)算的結(jié)果返回提供了一種便利的方法。
3.2 常量
R中還定義了一些常量,比如:
NA:表示不可用
Inf: 無窮
-Inf: 負(fù)無窮
TRUE:真
FALSE:假
4. R的基本使用
4.1 命令
R是一種語法非常簡單的表達(dá)式語言(expression language)。使用者通過命令(command)與R進(jìn)行交互。
基本命令要么是表達(dá)式(expressions)要么就是賦值(assignments)。如果一條命令是表達(dá)式,那么它將會被解析(evaluate),并將結(jié)果顯示在屏幕上,同時清空該命令所占內(nèi)存。賦值同樣會解析表達(dá)式并且把值傳給變量但結(jié)果不會自動顯示在屏幕上。
基于命令,可以用交互的方式或者批處理/腳本文件的方式使用R。
4.2 交互式使用 R
交互式shell是一種很方便的環(huán)境,可以進(jìn)行各種嘗試,隨時調(diào)整過程。與Python、Ruby等語言一樣,R也提供了shell環(huán)境。本文開始的例子就是以交互的方式使用R。當(dāng)打開R控制臺時,R會顯示命令提示符">",此時可以輸入命令。
下面是交互式使用R的幾個例子:
例一:
> help.start() #啟動在線幫助,會打開瀏覽器。
> x <- rnorm(50); y <- rnorm(x) #產(chǎn)生兩個隨機(jī)向量x和y
> plot(x,y) #使用x,y畫二維散點(diǎn)圖, 會打開一個圖形窗口
> ls() #查看當(dāng)前工作空間里面的 R 對象
> rm(x,y) #清除x,y對象
>x <- 1:20 # 相當(dāng)于x=(1,2,…,20)
例二:
x <- 1:20#等價(jià)于 x = (1, 2, ..., 20)。
w <- 1 + sqrt(x)/2#標(biāo)準(zhǔn)差的`權(quán)重'向量。
dummy <- data.frame(x=x, y= x + rnorm(x)*w)#創(chuàng)建一個由x 和 y構(gòu)成的雙列數(shù)據(jù)框
dummy #查看dummy對象中的數(shù)據(jù)。
fm <- lm(y ~ x, data=dummy)#擬合 y 對 x 的簡單線性回歸
summary(fm)#查看分析結(jié)果。
fm1 <- lm(y ~ x, data=dummy, weight=1/w^2)#加權(quán)回歸
summary(fm1)#查看分析結(jié)果。
attach(dummy)#讓數(shù)據(jù)框中的列項(xiàng)可以像一般的變量那樣使用。
lrf <- lowess(x, y)#做一個非參局部回歸。
plot(x, y)#標(biāo)準(zhǔn)散點(diǎn)圖。
lines(x, lrf$y)#增加局部回歸曲線。
abline(0, 1, lty=3)#真正的回歸曲線:(截距 0,斜率 1)。
abline(coef(fm))#無權(quán)重回歸曲線。
abline(coef(fm1), col = "red")#加權(quán)回歸曲線。
detach()#將數(shù)據(jù)框從搜索路徑中去除。
plot(fitted(fm), resid(fm),
xlab="Fitted values",
ylab="Residuals",
main="Residuals vs Fitted")一個檢驗(yàn)異方差性(heteroscedasticity)的標(biāo)準(zhǔn)回歸診斷圖。
qqnorm(resid(fm), main="Residuals Rankit Plot")#用正態(tài)分值圖檢驗(yàn)數(shù)據(jù)的偏度(skewness),峰度(kurtosis)和異常值(outlier)。
rm(fm, fm1, lrf, x, dummy)#再次清空。
例三: Michaelson 和 Morley 測量光速的經(jīng)典實(shí)驗(yàn)
filepath <- system.file("data", "morley.tab" , package="datasets")#從對象 morley 中得到實(shí)驗(yàn)數(shù)據(jù)的文件路徑
filepath#查看文件路徑
file.show(filepath)#查看文件內(nèi)容
mm <- read.table(filepath)#以數(shù)據(jù)框的形式讀取數(shù)據(jù)
mm$Expt <- factor(mm$Expt)
mm$Run <- factor(mm$Run)#將 Expt 和 Run 改為因子。
attach(mm)#讓數(shù)據(jù)在位置 3 (默認(rèn)) 可見(即可以直接訪問)。
plot(Expt, Speed, main="Speed of Light Data", xlab="Experiment No.")#用簡單的盒狀圖比較五次實(shí)驗(yàn)。
fm <- aov(Speed ~ Run + Expt, data=mm)#分析隨機(jī)區(qū)組,`runs' 和 `experiments' 作為因子。
summary(fm)
fm0 <- update(fm, . ~ . - Run)
anova(fm0, fm)#擬合忽略 `runs' 的子模型,并且對模型更改前后進(jìn)行方差分析。
detach()
rm(fm, fm0)#在進(jìn)行下面工作前,清空數(shù)據(jù)。
#下面是等高線和影像顯示的示例
x <- seq(-pi, pi, len=50)#x 是一個在區(qū)間 [-pi\, pi] 內(nèi)等間距的50個元素的向量
y <- x
f <- outer(x, y, function(x, y) cos(y)/(1 + x^2))#f 是一個方陣,行列分別被 x 和 y 索引,對應(yīng)的值是函數(shù) cos(y)/(1 + x^2) 的結(jié)果。
oldpar <- par(no.readonly = TRUE)
par(pty="s")#保存圖形參數(shù),設(shè)定圖形區(qū)域?yàn)椤罢叫巍薄?
contour(x, y, f)
contour(x, y, f, nlevels=15, add=TRUE)#繪制 f 的等高線;增加一些曲線顯示細(xì)節(jié)。
fa <- (f-t(f))/2#fa 是 f 的“非對稱部分”(t() 是轉(zhuǎn)置函數(shù))。
contour(x, y, fa, nlevels=15)#畫等高線
par(oldpar)# 恢復(fù)原始的圖形參數(shù)
image(x, y, f)
image(x, y, fa)#繪制一些高密度的影像顯示
objects();
rm(x, y, f, fa)#在繼續(xù)下一步前,清空數(shù)據(jù)。
th <- seq(-pi, pi, len=100)
z <- exp(1i*th)#1i 表示復(fù)數(shù) i
par(pty="s")
plot(z, type="l")#圖形參數(shù)是復(fù)數(shù)時,表示虛部對實(shí)部畫圖。這可能是一個圓。
w <- rnorm(100) + rnorm(100)*1i#假定我們想在這個圓里面隨機(jī)抽樣。一種方法將讓復(fù)數(shù)的虛部和實(shí)部值是標(biāo)準(zhǔn)正態(tài)隨機(jī)數(shù) ...
w <- ifelse(Mod(w) > 1, 1/w, w)#將圓外的點(diǎn)映射成它們的倒數(shù)。
plot(w, xlim=c(-1,1), ylim=c(-1,1), pch="+",xlab="x", ylab="y")
lines(z)#所有的點(diǎn)都在圓中,但分布不是均勻的。
#下面采用均勻分布。現(xiàn)在圓盤中的點(diǎn)看上去均勻多了。
w <- sqrt(runif(100))*exp(2*pi*runif(100)*1i)
plot(w, xlim=c(-1,1), ylim=c(-1,1), pch="+", xlab="x", ylab="y")
lines(z)
rm(th, w, z)#再次清空。
q()#離開 R 程序
4.3 工作空間(workspace)
R shell 可以任意地保存一個完整的環(huán)境,稱為工作空間(workspace)。前面的例子中,運(yùn)行q()命令退出R時,會被詢問是否要保存工作空間:

工作空間(workspace)保存了一些環(huán)境信息。每次與R的會話(session)可以從一個全新的環(huán)境開始,也可以在原來的基礎(chǔ)上繼續(xù),這些運(yùn)行信息就保存在工作空間中。
如果在UNIX系統(tǒng)以命令行的方式啟動R,則當(dāng)前目錄就是本次會話的工作空間:
$ mkdir r_test
$ cd r_test/
$ R
看看R能為工作空間保存些什么內(nèi)容:
> x <- rnorm(50); y <- rnorm(x) #產(chǎn)生兩個隨機(jī)向量x和y
> q()
Save workspace image? [y/n/c]: y
$ ls -Al
會發(fā)現(xiàn)R保存了兩個隱藏文件:.RData和.Rhistory。其中.RData以二進(jìn)制的方式保存了會話中的變量值,.Rhistory以文本文件的方式保存了會話中的所有命令。
如果在一個已有的工作空間中啟動R,會提示:
[原來保存的工作空間已還原]
此時可以用函數(shù)ls()和history()看到之前保存的數(shù)據(jù)和命令。
使用rm()/remove()可以刪除工作空間中的變量。
在R控制臺,也可以使用函數(shù)getwd()和setwd()來獲取/設(shè)置工作空間目錄;使用list.files()查看當(dāng)前目錄下的文件。
如果以GUI方式運(yùn)行R控制臺,可以通過菜單來加載或保存工作空間。
4.4 腳本/批處理
前面提到R可以在工作空間中保存歷史命令。其實(shí)這就是一個工作空間中的默認(rèn)腳本,當(dāng)加載工作空間時自動執(zhí)行。
我們完全可以寫自己的腳本,指定R批量執(zhí)行一些命令。通常,自己的腳本會以“.R”作為擴(kuò)展名。一個最簡單的例子test.R:
x <- rnorm(50); y <- rnorm(x) #產(chǎn)生兩個隨機(jī)向量x和y
plot(x,y) #使用x,y畫二維散點(diǎn)圖, 會打開一個圖形窗口
并保存到工作空間,然后在R控制臺,使用命令:
> source('test.R')
就可以執(zhí)行該腳本。
> source('test.R', echo=TRUE)可以讓腳本執(zhí)行時輸出更詳細(xì)的信息。
編寫腳本自動執(zhí)行一些任務(wù)時,sink()函數(shù)會比較有用:
> sink("record.lis")
會把所有后續(xù)的輸出結(jié)果從控制臺重定向到外部文件 record.lis 中,此時控制臺中看不到命令輸出的結(jié)果。使用命令:
> sink()
可以讓輸出流重新定向到控制臺。
5. 幫助系統(tǒng)
GNU軟件通常都會有非常好的幫助系統(tǒng),無論對于初學(xué)者還是熟練者都能帶來很大的幫助。R當(dāng)然也不例外。R中提供的幫助主要有以下幾種:
5.1 文檔和搜索
help.start() 命令會打開瀏覽器,顯示幫助文檔。包括一些入門的文檔,以及搜索功能(鏈接:Search Engine & Keywords)。

5.2 演示
demo()會按照包分組,列出所有可用的演示:

按照名稱可以開始演示,如:
demo(is.things)
5.3 函數(shù)幫助
如果已經(jīng)知道一個函數(shù)的名稱(比如solve),需要了解其所屬的包、用途、用法、參數(shù)說明、返回值、參考文獻(xiàn)、相關(guān)函數(shù)以及范例等,可以使用命令
help(solve)或 ?solve
該命令會彈出一個窗口:

5.4 函數(shù)示例
對于函數(shù),還可以使用example()執(zhí)行示例,比如:
example(solve)
5.5 關(guān)鍵字和運(yùn)算符
與函數(shù)的幫助類似,但是需要加上引號,如:
> ? '[[' # 等價(jià)于 help('[[')
> ?'+' #等價(jià)于 help('+')
> ?'if' #等價(jià)于 help('if')
5.6 搜索
如果不知道函數(shù)名稱,還可以進(jìn)行搜索,比如:
??'analysis' #等價(jià)于 search('analysis')

5.7 官方搜索
前面的幫助都受限于本地環(huán)境已經(jīng)安裝的包。如果要搜索R中所有的資源(包,函數(shù)、數(shù)學(xué)方法等),需要在R的官方網(wǎng)站搜索:
www.r-project.org—search.html
6. 學(xué)習(xí)資料
www.R-project.org R官方網(wǎng)站
cran.r-project.org—manuals.html 官方網(wǎng)站上的一些手冊和文檔(必看)
staff.washington.edu—Rcourse 華盛頓大學(xué)的一個R教程