//間瀬茂
COLOR(RED){SIZE(30){データフレームを作る、操作する}}

R の多くの関数はデータフレームと呼ばれるオブジェクトを対象とする.データフレームは、同じ長さの複数の数値ベクトル,文字ベクトル等を成分とする、data.frame属性を持つリストであるが,そのものとしては行列のような外見を持つ.各行・列はラベルを必ず持ち,それを用いた添字操作が可能である.データフレームの各行は一つの観測値(case)を表現する。データフレームの各列は一つの変数(項目)を表現する.

#contents
~

*データフレームを作る

**データファイルを SIZE(20){read.table()} 関数で読み込んでデータフレームを作る

データフレーム変数を得る基本は、特別の形式をもつデータファイルを SIZE(20){read.table()} 関数で読み込むことである。

***行ラベルのないデータファイル (header=TRUE)

行ラベルの無いデータファイル "temp1.data" の内容

 Price Floor Area Ch
 52.0  111.0 830  yes
 54.8  128.0 710  no
 57.5  101.0 1000 yes
 59.3  131.0 900  no

オプション header=TRUE 付きでデータフレームとして読み込む。最初の行は見出しで,列ラベルとされる。行ラベルは与えられておらず,自動的にヘッダー(通し番号 1,2,3,4)が付け加えられる

 > HP <- read.table("temp1.data", header=TRUE)
 > HP
   Price Floor Area  Ch   # 形式的に 4x4 行列.行・ラベルが自動的に付加される
 1  52.0   111  830 yes
 2  54.8   128  710  no
 3  57.5   101 1000 yes
 4  59.3   131  900  no
 > HP$Price                   # 第一列.HP[[1]] でも良い。
 [1] 52.0 54.8 57.5 59.3  # 数字は数値として読み込まれる
 > HP[["Ch"]]                  # これも可.第4列
 [1] yes no  yes no
 Levels: no yes          # 文字列は因子として読み込まれる
 > HP[1,]                 # 第一行.列ラベルが付く
   Price Floor Area  Ch
 1    52   111  830 yes
 > HP[2,]
   Price Floor Area Ch
 2  54.8   128  710 no
 > HP[2,2]               # 第2列第2行の要素
 [1] 128
 > HP[2,"Floor"]         # この形式も可
 [1] 128
 > dim(HP)               # 行列と同様次元を持つ
 [1] 4 4

***行ラベルつきのデータファイル (header=FALSE)

行ラベル "Am", "St", "Yo", "Ht" 付きのデータファイル "temp2.data" の内容

       Price  Floor  Area  Ch
 Am 52.0   111.0 830    yes
 St  54.8   128.0  710    no
 Yo 57.5   101.0  1000  yes
 Ht  59.3   131.0  900    no

(既定の) header=FALSE で読み込み

 > HP <- read.table("temp2.data") 
 > HP
   Price Floor Area  Ch
 Am  52.0   111  830 yes
 St  54.8   128  710  no
 Yo  57.5   101 1000 yes
 Ht  59.3   131  900  no
 > HP[2,2]        # 第2行第2列成分
 [1] 128
 > HP["St","Area"] # 第2行第3列成分
 [1] 710
 > HP["St","Ch"] # 第2行第4列成分
 [1] no
 Levels: no yes

もう一つの行ラベル付きデータファイル "temp3.data"。行ラベルは文字列 "32", "13", "5", "71" と見なされる

      Price  Floor   Area  Ch
 32 52.0   111.0  830    yes
 13 54.8   128.0  710    no
 5   57.5   101.0 1000   yes
 71 59.3   131.0  900    no

 > HP <- read.table("temp3.data")  # 既定値の header=FALSE で読み込み
 > HP
    Price Floor Area  Ch
 32  52.0   111  830 yes
 13  54.8   128  710  no
 5   57.5   101 1000 yes
 71  59.3   131  900  no
 > HP[32,2]     # エラー
 [1] NA
 > HP["32",2]   # 正しい.HP[1,2] でも良い
 [1] 111

*** 列(i.e. 変数名)ラベルの無いデータファイル

 a  1  2 yes    # 列ラベルの無いデータファイル "temp.data"
 b  2  3  no
 c  5  7 yes

 > x=read.table("temp.data")  # 既定の header=FALSE で読み込み
 > x
   V1 V2 V3  V4    # 列(変数名)ラベルが自動的につけられる
 1  a  1  2 yes
 2  b  2  3  no
 3  c  5  7 yes
 > y=read.table("temp.data",header=TRUE)
 > y
   a X1 X2 yes    # ナンセンスな結果
 1 b  2  3  no
 2 c  5  7 yes

**データフレームを直接作る。関数 data.frame()

*** 数値ベクトルからデータフレームを作る

 > data.frame(vx = 1:4, vy = rnorm(4))   # 4x4 のデータフレーム。列ラベル vx,vy 
    vx          vy
 1 1   -0.8481768
 2 2    0.8831475
 3 3    0.2178012
 4 4    0.2753476

*** 数値行列からデータフレームを作る

 > x
      [,1] [,2] [,3]
 [1,]    1    5    9
 [2,]    2    6   10
 [3,]    3    7   11
 [4,]    4    8   12
 > data.frame(x)
   X1 X2 X3
 1  1  5  9
 2  2  6 10
 3  3  7 11
 4  4  8 12  
 > data.frame(x,row.names=c("a","b","c","d"))  # 行ラベルを指定
   X1 X2 X3   # 列ラベルは後から変更するしかない(?)
 a  1  5  9      # x が列ラベルを持つ行列なら、それを継承する
 b  2  6 10
 c  3  7 11
 d  4  8 12
 
 > x=matrix(1:4, c(2,2), dimnames=list(c("Ca","Cu"),c("Ag","Pt")))
 > x           # 行・列ラベル付き行列
    Ag Pt
 Ca  1  3
 Cu  2  4
 > data.frame(x)  # データフレームは行・列ラベルを継承する
    Ag Pt
 Ca  1  3
 Cu  2  4

** 行列をデータフレームとしてファイルに記録し、それをまた読み込む。write.table(), read.table() 関数 (2003.12.25)
注意:MASS ライブラリ中の write.matrix 関数も write.table 関数と同様の機能を持つ。

 > x <- matrix(1:12, ncol=3)  # 数値行列
 > x
      [,1] [,2] [,3]
 [1,]    1    5    9
 [2,]    2    6   10
 [3,]    3    7   11
 [4,]    4    8   12
 > write.table(x, file="temp.dataframe")  # x をファイルに書き出す(同時にデータフレームに強制変換される)
 > xx <- read.table("temp.dataframe")   # 再び読み込み
 > xx                                                     # データフレームになっている                
   X1 X2 X3                                           # 変数ラベルが付け加えられている  
 1  1  5  9
 2  2  6 10
 3  3  7 11
 4  4  8 12

 "X1" "X2" "X3"         # ファイル temp.dataframe の中身は
 "1" 1 5 9
 "2" 2 6 10
 "3" 3 7 11
 "4" 4 8 12

*  データフレームの操作

** 列の消去

 > HP[[2]] <- NULL  # 第2列を消去
 > HP
       Price  Area  Ch
 32  52.0   830    yes
 13  54.8   710    no
 5    57.5  1000   yes
 71  59.3   900    no

**列の置き換え

 > HP[[2]] <- c(1,2,3,4)   # 第2列を置き換え
 > HP
       Price Floor Area  Ch
 32  52.0     1    830   yes
 13  54.8     2    710   no
 5    57.5     3   1000  yes
 71  59.3     4    900   no

**サブデータフレームの取り出し

 > HP[c(1,3,4),]     # 第1,3,4行を抜き出す(結果もデータフレーム)
       Price Floor Area  Ch
 32  52.0     1    830    yes
 5    57.5     3   1000   yes
 71  59.3     4    900    no 

** 行・列ラベルの取り出し、変更

 > rownames(HP)   # 行ラベルの取り出し
 [1] "32" "13" "5"  "71"
 > colnames(HP)   # 列ラベルの取り出し
 [1] "Price" "Floor" "Area"  "Ch"
 > colnames(HP) <- c("P","F","A","C") # 列ラベルの変更
 > HP
       P   F    A   C
 32 52.0 111  830 yes
 13 54.8 128  710  no
 5  57.5 101 1000 yes
 71 59.3 131  900  no
 > rownames(HP) <- c("01","02","03","04") # 行ラベルの変更
 > HP
       P   F    A   C
 01 52.0 111  830 yes
 02 54.8 128  710  no
 03 57.5 101 1000 yes
 04 59.3 131  900  no
 > rownames(HP) <- c("1","2","3","4") # 両者は同じ効果を持つ
 > rownames(HP) <- c(1,2,3,4)

**SIZE(20){cbind()} で行ラベルが同じ二つのデータフレームを連結  (つまり、変数を増やす)

 > x            # 第1のデータフレーム
   Rooms  Color
 1     4    Red
 2     6  Brown
 3     7 Yellow
 4     3   Grey
 > y            # 第2のデータフレーム
    Price Floor Area  Ch
 1  52.0   111  830 yes
 2  54.8   128  710  no
 3  57.5   101 1000 yes
 4  59.3   131  900  no
 > z <- cbind(y,x)
 > z            # 結合されたデータフレーム
     Price Floor Area  Ch Rooms  Color
 1  52.0   111  830   yes     4      Red
 2  54.8   128  710   no      6      Brown
 3  57.5   101 1000  yes     7     Yellow
 4  59.3   131  900   no      3      Grey

**SIZE(20){rbind()} で列ラベルが同じ2つのデータフレームを連結 (つまりデータ数を増やす)

 > y
     Price Floor Area  Ch
 1  52.0   111  830   yes
 2  54.8   128  710   no
 3  57.5   101 1000  yes
 4  59.3   131  900   no
 > yy
   Price Floor Area  Ch
 5  62.0   109  720 yes
 6  85.8   182  650  no
 7  72.5   115  567 yes
 > rbind(y,yy)
   Price Floor Area  Ch
 1  52.0   111  830  yes
 2  54.8   128  710  no
 3  57.5   101 1000 yes
 4  59.3   131  900  no
 5  62.0   109  720  yes
 6  85.8   182  650  no
 7  72.5   115  567 yes

 > rownames(yy)<-c(3,4,7,8)  # わざと y と yy の行ラベルが一部一致するようにする
 > yy
   Price Floor Area  Ch
 3  52.0   111  830 yes
 4  54.8   128  710  no
 7  57.5   101 1000 yes
 8  59.3   131  900  no
 > rbind(y,yy)
    Price Floor Area  Ch
 1   52.0   111  830 yes
 2   54.8   128  710  no
 3   57.5   101 1000 yes
 4   59.3   131  900  no
 31  52.0   111  830 yes # 重複する行ラベルは自動的に付け替えられる
 42  54.8   128  710  no # 重複する行ラベルは自動的に付け替えられる
 7   57.5   101 1000 yes
 8   59.3   131  900  no

**データフレームを行列に変換。関数 data.matrix()

 > HP                              # これはデータフレーム
    Price Floor Area  Ch
 32  52.0   111  830 yes
 13  54.8   128  710  no
 5   57.5   101 1000 yes
 71  59.3   131  900  no
 > x <- data.matrix(HP)  
 > x                                # これはただの行列 (見たところ同じ)
    Price Floor Area Ch   # 行・列ラベルをしっかり継承
 32  52.0   111  830  2   # 因子 Ch はその内部表現である数値に変換されている
 13  54.8   128  710  1
 5   57.5   101 1000  2
 71  59.3   131  900  1
 > attributes(HP)            # HP の属性をみる
 $names                        # 列(変数)名
 [1] "Price" "Floor" "Area"  "Ch" 
 $class
 [1] "data.frame"            # 確かに data.frame 属性を持つ
 $row.names                  # 行(データ)名
 [1] "32" "13" "5"  "71"
 
 > attributes(x)               # x の属性をみる
 $dim
 [1] 4 4
 $dimnames
 $dimnames[[1]]            # これは行列の行ラベル
 [1] "32" "13" "5"  "71"
 $dimnames[[2]]            # これは列ラベル
 [1] "Price" "Floor" "Area"  "Ch"
 > str(x)                         # str() 関数の結果も確かに異なる
  num [1:4, 1:4] 52 54.8 57.5 59.3 111 128 101 131 830 710 ...
  - attr(*, "dimnames")=List of 2
   ..$ : chr [1:4] "32" "13" "5" "71"
   ..$ : chr [1:4] "Price" "Floor" "Area" "Ch"

*データフレームに関する情報を得る

** データフレームに関する詳細な情報。関数 str()

 > HP                               # データフレーム
    Price Floor Area  Ch
 32  52.0   111  830 yes
 13  54.8   128  710  no
 5   57.5   101 1000 yes
 71  59.3   131  900  no
 > str(HP)                      # データフレームの詳細
 `data.frame':   4 obs. of  4 variables:
  $ Price: num  52 54.8 57.5 59.3  # HP$Price は数値ベクトル
  $ Floor: num  111 128 101 131  #
  $ Area : int  830 710 1000 900   # HP$Area は整数値ベクトル
  $ Ch   : Factor w/ 2 levels "no","yes": 2 1 2 1 # no, yes は因子 2, 1 と解釈されている

** データフレームオブジェクトかどうか検査。関数 is.data.frame()
 
  > is.data.frame(HP) # データフレームオブジェクトか?
 [1] TRUE                  # 然り


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