[SAS] 在SAS/Base實作R.再探


前陣子寫過一篇文章介紹了Xin Wei (2012)於期刊Journal of Statistical Software發表的論文,裡頭作者提供了一個SAS MACRO可以將R語言強大的矩陣運算與圖形化能力十分完整地與SAS/Base無縫整合起來。

這陣子經過不少測試之後,我發現這個MACRO有一些地方可以再強化,所以對它進行了一些修改。這篇文章主要想談一談這個MACRO的一些限制與我對它做的一些小小變革。

我的測試環境主要是Windows Server 2k3 (32-bit)、SAS 9.1.2與R 2.15.2 (Trick or Treat!)。

首先是關於%PROC_R在資料轉換的時候,的路徑問題。我發現%PROC_R用來指定欲轉換資料的data set名稱的引數,「不完全」支援libref,也就是「不完全」支援WORK(暫存資料表路徑)以外的永久資料表路徑。這裡如果使用了libref作為前引的名稱,後續在做R coding的時候會有點雞毛蒜皮的問題(最起碼的問題就是R data frame物件名稱會有點無謂地長……),所以我決定把libref給明確地導出來,讓資料轉換之間在SAS裡、R裡的命名與對應的資料路徑體系更明確。



這意味著如果要在R code裡頭圖命名的方便,想要丟到R的SAS資料表以及R運算完想丟回來的data frame,都必須先丟到WORK,這就不是很方便了。原作者在SAS2R這個部分,SAS source code是以下這一塊:



這邊我把它改寫成:



此外在R2SAS的部分也要類推修改,邏輯完全比照辦理。如此一來,就能允許SAS2R以及R2SAS這兩個引數都支援兩段式命名呼叫資料表之餘,又不必讓他們冗長地出現在R物件的名稱上,只要一次性地在引數裡頭自由指定從哪個資料表路徑丟出資料、又要從哪個資料表路徑接回資料即可,後續都以memname來看待並處理物件/表單。



接下來則是得處理我遇到的一個比較大的困擾。
針對呼叫R的動作,原作者採用的是X command unnamed pipe的方式,程式碼如下:



非常簡潔。
但這個noxwait與xsync似乎大有問題。這兩個選項,根據SAS官方文件,前者是用來決定Win cmd執行後是否需要手動exit退回SAS程序,noxwait就是執行完自動退回;而xsync則是讓SAS session在cmd執行完畢之前都先凍結,不往下跑。

當然,如果不這麼做,就沒辦法等到R運算完成,然後由SAS接手結果級。

問題是,我發現在用R運算大量資料時(少量的運算沒問題!),這個系統似乎會失靈。可能是我測試的環境的什麼因素的影響,我研究了半天也理不出頭緒,但總而言之我發現這兩個系統選項都無法真正讓SAS去等R運算完成,所以就會導致%PROC_R後半段失靈,你不會在SAS裡頭看到R的執行結果LOG,因為SAS想去接的時候R根本還沒跑完!理論上SAS應該要等R,但它沒有等。(好杯桑)

好吧,既然不知道原因,只好繞道而行,我們改SYSTASK這條路,於是程式碼改寫為下:



如此一來,問題就解決了。
(正確來說是華麗地迴避惹~)
關於X command與SYSTASK的差異,這篇文章有不錯的說明。

直接看結論:

...that by default the SYSTASK command executes asynchronously, whereas the X command is synchronous therefore you have to wait for control to return to SAS. However, XWAIT/ NOXWAT, XSYNC/NOXSYNC options for X command and WAIT/ NOWAIT, WAITFOR options for SYSTASK command can help you to control the way you want either of these commands to be executed.

話是這麼說,但我遇到的問題就是X command的xsync和xwait都失靈。
這篇文章並沒有替我解惑。
管它的。

0 comment(s):

Post a Comment

回應文章前請注意下列三勿原則:

1)勿拍照;(→會有靈異的照片從你的相機裡跑出來...
2)勿餵食;(→會有飢渴的猛獸從我的網誌裡跑出來...
3)勿告白。(→會有奇怪的東西從站長體內裡跑出來...

謝謝大家的配合。
( > ー <)b