[[FrontPage]]


#contents

2014/03/16からのアクセス回数 &counter;

ここで紹介したSageワークシートは、以下のURLからダウンロードできます。

http://www15191ue.sakura.ne.jp:8000/home/pub/37/

また、Sageのサーバを公開しているサイト(http://www.sagenb.org/, http://www15191ue.sakura.ne.jp:8000/)にユーザIDを作成することで、ダウンロードしたワークシートを
アップロードし、実行したり、変更していろいろ動きを試すことができます。

* RとPandas(Sage)でのデータフレームの相互変換 [#gafaa199]

これまで、RのグラフをSageで表示したり、RとSage間でのデータの受け渡しを紹介してきましたが、
Rでもっともよく使われるデータフレームについて、まったく考えていませんでした。

しかし、Pandasの機能が強力であり、とても使えるツールであることからRとPandas間のデータフレーム
を相互変換することに挑戦してみます。

また、Rのグラフ表示で使っていたRUtil.pyもPNGファイルベースとして高速化をはかり、ここにデータフレーム
の相互変換機能を追加することになりました。

新たに追加したデータフレーム変換関数は、以下の2個です。

- RDf2PandaDf: RのデータフレームをPandasのデータフレームに変換する

- PandaDf2RDf: PandasのデータフレームをRのデータフレームに変換する


** データ変換で使用するパッケージとライブラリ [#td17d16a]

データフレーム変換で使用するSageのライブラリーは、pandasとnumpyです。
Rは、jsonliteをパッケージを使用します。

sageへの入力:
#pre{{
# RとPandasのデータフレームを相互に変換する方法
# Sageでは、numpyとpandasをインポート
import pandas as pd
import numpy as np
# Rではjsonliteパッケージを使用
r('library(jsonlite)')
# 例としてR Graphic Cookbookのデータを使用
#r("install.packages('gcookbook')")
r('library(gcookbook)')
}}
#pre{{
[1] "jsonlite"  "gcookbook" "stats"     "graphics"  "grDevices" "utils"     "datasets"  "methods" 
[9] "base"    
}}


** RからPandasへのデータフレーム変換 [#j9d59b2a]

RからPandasにデータフレームを変換するために、jsonliteのtoJSONとPandasのread_json関数を使用します。

以下にgcookbookのサンプルデータheightweightをRからPandasのデータフレームに変換する例を示します。

sageへの入力:
#pre{{
# RからJSON形式でデータを持ってくる方法
# 例として、gcookbookのサンプルデータをRから取得する
test_json = r('toJSON(heightweight, pretty=FALSE)')
heightweight = pd.read_json(sageobj(test_json)); heightweight.head()
}}
#pre{{
   ageMonth  ageYear  heightIn sex  weightLb
0       143    11.92      56.3   f      85.0
1       155    12.92      62.3   f     105.0
2       153    12.75      63.3   f     108.0
3       161    13.42      59.0   f      92.0
4       191    15.92      62.5   f     112.5

[5 rows x 5 columns]
}}


*** 関数にまとめる [#g2e218b3]

上記の処理をRDfPandasDfという関数にまとめると以下の様になります。


sageへの入力:
#pre{{
# これを関数にまとめる
# Rのデータフレームをpandasのデータフレームに変換する
def RDf2PandaDf(name):
    json_str =  r('toJSON(%s, pretty=FALSE)' % name)
    return pd.read_json(sageobj(json_str))
}}


*** RDf2PandasDfの使用例 [#u9e0761e]

RDf2PandasDfを使ってgcookbookのサンプルデータheightweightをRからPandas(Sage)
にデータを持ってくる場合の例です。

Rのデータフレーム名をRDf2PandasDfの引数とするとPandasのデータフレームに変換されて返されます。

sageへの入力:
#pre{{
print RDf2PandaDf('heightweight').head()
}}
#pre{{
   ageMonth  ageYear  heightIn sex  weightLb
0       143    11.92      56.3   f      85.0
1       155    12.92      62.3   f     105.0
2       153    12.75      63.3   f     108.0
3       161    13.42      59.0   f      92.0
4       191    15.92      62.5   f     112.5

[5 rows x 5 columns]
}}


** PandasからRへのデータフレームに変換 [#q686ce53]

今度は、逆にPandasのデータフレームをRのデータフレームに変換します。
いろいろ試したのですが、writeJSONを使った変換では上手く処理できず、
もっともオーソドックスなカラム名とデータフレームのvaluesをzipとdictを
使って辞書の配列に変換する方式に行き着きました。

sageへの入力:
#pre{{
# 同様に関数にまとめる
# pandasのデータフレームをRに渡す
def PandaDf2RDf(df, name):
    l = [dict(zip(df.columns, x)) for x in df.values.tolist()]
    json_str = str(l)
    json_str = json_str.replace("'", '\\"')
    r('%s <- fromJSON("%s")' % (name, json_str))
}}


*** PandaDf2RDfの使用例 [#hb5f4e28]

年齢と性別のデータフレームをPandasで作成し、それをPandaDf2RDfを使って
Rのデータフレームに変換します。

sageへの入力:
#pre{{
# PandasのデータをRに渡す
age = [20, 22, 25, 27, 21, 23, 37, 31, 61, 45, 41, 32]
sex = ['F', 'M', 'M', 'M', 'F', 'M', 'F', 'M', 'F', 'M', 'F', 'M']
df = pd.DataFrame({'age': age, 'sex': sex}); df.head()
}}
#pre{{
  age sex
0  20   F
1  22   M
2  25   M
3  27   M
4  21   F

[5 rows x 2 columns]
}}


PandaDf2RDfの引数は、変換するデータフレームとRでのデータフレーム変数名です。

以下の例では、上記で作成したdfをRのデータフレームに変換し、aという変数にセットし、
それをSageのr関数を使って表示しています。きちんと変換できているのが確認できます。


sageへの入力:
#pre{{
PandaDf2RDf(df, "a")
r('a')
}}
#pre{{
   age sex
1   20   F
2   22   M
3   25   M
4   27   M
5   21   F
6   23   M
7   37   F
8   31   M
9   61   F
10  45   M
11  41   F
12  32   M
}}

** コメント [#p46ea21d]
#vote(おもしろかった[2],そうでもない[0],わかりずらい[0])

皆様のご意見、ご希望をお待ちしております。
- rpy2/R interface に DataFrame の変換が書いてあり ipython で動きました。http://pandas.pydata.org/pandas-docs/stable/r_interface.html -- [[ysato ]] &new{2014-03-26 (水) 11:35:56};
- $sage -ipython notebook で実行してみました。残念んsがら動きません。json が原因のように思われます。代替えとして rpy2  を使って変換しています。 -- [[ysato]] &new{2014-10-11 (土) 10:33:33};
- $sage -ipython notebook で動かした例を次ぎに載せました。http://mmays.hatenablog.com/entry/2014/10/11/163928 -- [[ysato]] &new{2014-10-11 (土) 16:47:41};
- ysatoさま、Sageのnotebookの中でFile..., Action, Data..., sageの最後のsageメニューでpythonやrを選択すれば、そのままSageの中のpythonやRが実行できます。お試し下さい。 -- [[竹本 浩]] &new{2014-10-12 (日) 09:26:51};
- Sage 6.3 のnotebook で実行してみました。「# RからJSON形式でデータを持ってくる方法」のセルを evaluate するとエラーになります。「PandasからRへのデータフレームに変換」は正常に動きます。コピーしてペーストしたので入力ミスは無いと思います。 チェックをお願いいたします。 -- [[ysato]] &new{2014-10-16 (木) 18:17:00};
- ysatoさま、Sage6.3ではsageobjの戻り値に['DATA']をつけて下さい。以下のサイトを参照してください。http://www15191ue.sakura.ne.jp:8000/home/takepwave/47/ -- [[竹本 浩]] &new{2014-10-18 (土) 09:56:06};
- url をクリックしたのですが次のメッセージでアクセスできません。You do not have permission to access this worksheet -- [[ysato]] &new{2014-10-18 (土) 10:55:55};
- ysatoさま、失礼しました。リンクを間違えました。http://www15191ue.sakura.ne.jp:8000/home/pub/47 -- [[竹本 浩]] &new{2014-10-18 (土) 11:33:21};
- 成功しました。ありがとうございました。 -- [[ysato]] &new{2014-10-18 (土) 13:46:52};

#comment_kcaptcha

トップ   編集 差分 バックアップ 添付 複製 名前変更 リロード   新規 一覧 単語検索 最終更新   ヘルプ   最終更新のRSS
SmartDoc