No.21955 Rの論理ベクトル  【明石】 2016/03/31(Thu) 21:33

青木先生 様;

お忙しいところを失礼いたします,明石と申します。

過日は,Rプログラミングについて丁寧なご教示をいただき,誠にありがとうございました。
改めて御礼を申し上げます。

今回は,Rの論理ベクトルについて,ご教示をいただきたいと思います。
どうぞよろしくお願いいたします。

−−−

以下の2つのファイルを用いた,条件抽出の問題です。

"dat.csv"  ;データファイル

 m 行 n 列のデータフレーム
 行; 事例
 列; 項目(カテゴリカル変数)
    項目名; item_1, item_2, item_3, , , , , item_n
    項目値; "C_1", "C_2", "C_3" などの文字列

"rule.csv"  ;条件抽出ルールを記述したファイル

 r 行 1 列のデータフレーム

 ルールの記述例;
 item_1="C_1" & item_2="C_4"
  item_3="C_2" & item_5="C_4" & item_8="C_8"
 ...............

処理手順は,以下の通りです。

(1) データファイル "dat.csv" の読み込み

dat <- read.table("dat.csv", header=TRUE, sep="," , row=1)

(2) ルールファイル "rule.csv" の読み込み,条件抽出

ループを回して,1つづつルールを取り出し,条件抽出式に変換します。

最終的に,データファイルの各事例に, r 個のルールを適用した結果の論理ベクトルを得ます。
(「星取表」と呼びます)

(3) 結果ファイル

上記の星取表を出力します。

 m 行 r 列のデータフレーム
 行; 事例
 列; ルール名

先生にお聞きしたいことは,(2) のプログラムです。

(Q1)

以下にお示ししますように,ルールから条件抽出式を組み立てる際に,
どのような文字列操作を行えばよいのか。

ルールに含まれている "" を,どのように扱えばよいのか,苦慮しています。

【ルール】
item_1="C_1" & tem_2="C_4"

【条件抽出式】
dat$item_1=="C_1" && item_2=="C_4"

(Q2)

文字列操作により,条件抽出式を得たとします。

このままでは文字列ですので,論理ベクトルを得ることはできません。

"dat$item_1=="C_1" && item_2=="C_4""

文字列 "dat$item_1=="C_1" && item_2=="C_4"" を,
条件抽出式とした扱うためには,どのようにすればよいのか,苦慮しています。

以上2点,ご教示をいただければ助かります。

どうぞ,よろしくお願いいたします。
//明石

No.21956 Re: Rの論理ベクトル  【青木繁伸】 2016/04/01(Fri) 00:59

dat.csv のテストデータ
item_1,item_2,item_3,item_4,item_5
C_2,C_5,C_5,C_5,C_1
C_4,C_1,C_2,C_5,C_4
C_3,C_4,C_4,C_4,C_3
C_1,C_3,C_5,C_4,C_2
C_5,C_1,C_4,C_1,C_1
C_1,C_4,C_4,C_3,C_1
C_3,C_2,C_3,C_4,C_2
C_5,C_1,C_3,C_2,C_3
C_3,C_2,C_2,C_2,C_2
C_3,C_5,C_1,C_2,C_5
rule.csv のテストデータ
item_1="C_1" & item_2="C_4"
item_3="C_2" & item_5="C_4" & item_2="C_1"
のように
& は && ではなく 1 文字
= も == ではなく 1 文字
で入力されているとする

プログラム
dat <- read.table("dat.csv", header=TRUE, sep=",") # row 引数とは?
m <- nrow(dat)
rule <- readLines("rule.csv") # ベクトルとして読み込む
r <- length(rule)
result <- matrix(logical(m*r), m)
for (i in seq_len(r)) {
r <- gsub("=", "==", rule[i])
result[,i] <- with(dat, eval(parse(text=r)))
}
result
出力
> result
[,1] [,2]
[1,] FALSE FALSE
[2,] FALSE TRUE
[3,] FALSE FALSE
[4,] FALSE FALSE
[5,] FALSE FALSE
[6,] TRUE FALSE
[7,] FALSE FALSE
[8,] FALSE FALSE
[9,] FALSE FALSE
[10,] FALSE FALSE
with(dat, eval(parse(text=r))) が,肝!

No.21957 【御礼】 Re: Rの論理ベクトル  【明石】 2016/04/01(Fri) 06:06

青木先生 様;

お忙しいところを失礼いたします,明石と申します。

今回も丁寧なご教示をいただき,誠にありがとうございました。

大変に勉強になりました。
技を勉強させていただきます。

心から御礼を申し上げます。

No.21959 Re: Rの論理ベクトル  【明石】 2016/04/01(Fri) 21:28

青木先生 様;

お忙しいところを失礼いたします,明石と申します。

ご丁寧にご教示いただき,誠にありがとうございました。
追試を行い,理解できました。

"rule.csv" のテストデータは,以下のようでした。
item_1="C_1" & item_2="C_4"
item_3="C_2" & item_5="C_4" & item_2="C_1"

別の形式として,
Rの連関ルール(aRuleパッケージ)の出力
lhs(条件部) → rhs(結論部)
のlhs(条件部)の場合を読み込んだ場合の検討をしています。

item_1=C_1, item_2=C_4
item_3=C_2, item_5=C_4, item_2=C_1

これを,"rule2.csv" とします。

"rule2.csv" を読み込んで,青木先生のプログラムが利用できるように,
前処理のプログラムを作成しました。

動作は確認できましたが,文字列操作の改善の余地があると思われます。

シンプルに書ける方法をご教示いただければ,勉強になります。
どうぞ,よろしくお願いいたします。

# データファイルの読み込み

dat <- read.table("dat.csv", header=TRUE, sep=",")
m <- nrow(dat)

# ルールファイルの読み込み(連関ルールの lhs部)

v <- readLines("rule2.csv") # ベクトルとして読み込む

r <- length(v)

# 青木先生のプログラムが利用できるように,前処理の追加

qr <- NULL

for(i in 1:r) {
  b <- strsplit(v[i], ", ")
  b <- unlist(b)
  n <- length(b)
  for(k in 1:n) {
    a <- b[k]
    d <- strsplit(a, "=")
   d <- unlist(d)
   d1 <- d[1]
   d2 <- d[2]
   d <- paste(d1, "=", "\"", d2, "\"", sep="")
    b[k] <- d
  }
b <- paste(b, sep="", collapse=" & ")
qr <- rbind(qr, b)
}

rule <- as.vector(qr)

# 青木先生〜

r <- length(rule)

result <- matrix(logical(m*r), m)

for (i in seq_len(r)) {
r <- gsub("=", "==", rule[i])
result[,i] <- with(dat, eval(parse(text=r)))
}

result

# 〜青木先生

result <- result + 0

write.csv(result, "星取表2.csv")

No.21960 Re: Rの論理ベクトル  【青木繁伸】 2016/04/02(Sat) 09:11

結果として,動けばどのようにプログラムしてもよいのですが,調べることも含めてプログラムを書く時間が短く,結果としてのプログラムが短ければうれしいでしょうね。

ということで,for の中の r を定義する部分を書き換えます(gsub を使えばよいことが示唆されていましたね)。

r <- gsub("=", "==", gsub('(C_[0-9])', '"\\1"', gsub(",", " &", rule[i])))

, を &
C_* を "C_*" にしてから(* は 0~9)
= を == にします。
gsub ごとに 3 行に分けて書くとわかりやすいかも。

No.21961 【御礼】 Re: Rの論理ベクトル  【明石】 2016/04/02(Sat) 12:25

青木先生 様;

お忙しいところを失礼いたします,明石と申します。

今回も丁寧なご教示をいただき,誠にありがとうございました。

大変に勉強になりました。
正規表現を使う技を勉強させていただきます。

心から御礼を申し上げます。

● 「統計学関連なんでもあり」の過去ログ--- 048 の目次へジャンプ
● 「統計学関連なんでもあり」の目次へジャンプ
● 直前のページへ戻る