R語言編程藝術(5)R語言編程進階

本文對應《R語言編程藝術》算法

第14章:性能提高:速度和內存;數據庫

第15章:R與其餘語言的接口;編程

第16章:R語言並行計算數組

 

=========================================================================緩存

性能提高:速度和內存app

要使R代碼運行速度更快,有如下建議:函數

  1. 經過向量化的方式優化、使用字節碼編譯等;
  2. 將代碼中最消耗CPU的核心部分用編譯型語言編寫,如C或C++;
  3. 將代碼用某種並行的方式編寫。

 

消除顯示循環:性能

採用向量化提高速度,由於採用顯示循環涉及屢次函數調用和迭代,耗費時間,而向量化函數內部是用編譯型語言實現,所以會提高速度。優化

經常使用的加速代碼的向量化函數:ifelse() /which() /where() /any() /all() /cumsum() /cumprod()等函數;用於矩陣的rowSums() /colSums()等函數;用於窮舉全部組合問題的combn() /outer() /lower.tri() /upper.tri() /expand.grid()等函數。spa

儘管apply()能夠消除顯式循環,但它其實是用R而不是C實現的,所以它一般並不能加速代碼,只是使代碼更加緊湊。然而,其餘的apply函數,如lapply(),對於加速代碼是很是有幫助的。

 

利用Rprof()來尋找代碼的瓶頸:

首先調用Rprof()來開啓監視器,而後運行代碼,再調用帶NULL參數的Rprof()來結束監視。最後,調用summaryRprof()來查看結果。

 

內存管理:

數據分塊:read.table()函數的skip參數設置,能夠分塊讀取數據。

R軟件包的內存管理:RMySQL,提供R與MySQL的接口,將選擇數據的操做放在數據庫端;biglm包,能夠在很是大的數據集上進行迴歸和廣義線性模型的分析;ff包,經過將數據存放在硬盤上來回避內存的限制;bigmemory包,功能相似,但它不只能夠將數據存儲在硬盤上,還能夠將數據保存在機器的主內存中,這對於多核的機器而言是一個理想的選擇。

 

 

=========================================================================

R與其餘語言的接口

能被R調用的C/C++函數:

通常而言,這樣作的目的是提高程序的性能;另外一個緣由是使用特殊的I/O操做(例如R使用的TCP協議速度不如C/C++使用的UDP協議)。

接口能夠經過.C()或.Call()實現。.Call()提供了更全面的功能,但使用它須要對R的內部結構有所瞭解。

注意:C語言中,二維數組是按行進行存儲的,而在R中則是按列存儲;C語言下標是從0開始,而在R中是從1開始。

 

從Python調用R:

Python缺乏內置的統計和數據處理功能,能夠經過R來彌補。

RPy是一個Python模塊,容許在Python中使用R。若是但願有額外的性能提高,則能夠考慮與NumPy共同使用。

語法:R中的對象(函數)名冠上r.前綴。

注意:Python的語法中沒有波浪號,所以在指定模型表達式時須要使用字符串;

須要一個數據框來包含數據;

若是R的函數名中帶有英文句點,那麼須要在Python中改成下劃線。

 

>>> r.library(‘lattice’)
>>> r.assign(‘a’, a)
>>> r.assign(‘b’, b)
>>> r(‘g <- expand.grid(a, b)’)
>>> r(‘g$Var3 <- g$Var1^2 + g$Var1 * g$Var2’)
>>> r(‘wireframe(Var3 ~ Var1 + Var2, g)’)
>>> r(‘plot(wireframe(Var3 ~ Var1 + Var2, g))’)

 

  

=========================================================================

R語言並行計算

Snow包簡介:主要過程:

  1. 加載代碼
  2. 加載snow包
  3. 建立snow集羣
  4. 創建相關的鄰接矩陣
  5. 在建立的集羣上針對鄰接矩陣運行代碼

 

OpenMP包:

利用R調用並行化的C

經常使用指令:

#pragma omp barrier

迭代型算法中經常使用,線程將在屏障處進行等待,直到每次迭代的結束

#pragma omp critical

{

    // place one or more statements here

}

緊接着這一指令的代碼塊稱爲一個「關鍵區域」(critical section),意思是在這個區域中同時只容許一個線程執行這段代碼

#pragma omp single

{

    // place one or more statements here

}

緊接着這一指令的代碼塊將只被一個線程執行

 

簡單並行(embarrassingly parallel):

指那些線程與線程之間不須要進行交互的並行方式,它們每每只須要將原始的程序稍加修改便可實現並行。這樣,不只編寫簡單,並且有着極地的通訊開銷。

 

靜態和動態任務分配:

整體來講,動態任務分配由於有可能產生嚴重的緩存開銷,所以實際上性能不如靜態分配。

相關文章
相關標籤/搜索