datamining r 4th

14
R: k最近点分類 apply関数 瀬々 潤 [email protected] 2009/11/19

Upload: sesejun

Post on 11-Jun-2015

652 views

Category:

Documents


0 download

TRANSCRIPT

Page 1: Datamining r 4th

R: k最近点分類

apply関数瀬々 潤

 [email protected] 2009/11/19

Page 2: Datamining r 4th

USPSデータについて

Page 3: Datamining r 4th

訓練データとテストデータ• すべての訓練データとテストデータは,ある数字か否かを当てるものになっている• 「2か2でないか」などという問題になっている• usps/usps_2_train.tab は数字「2」の訓練データ• usps/usps_2_test.tab は数字「2」のテストデータ• 通常テストデータには「クラス」は無いが,ここでは便宜的に正しいクラスを入れてある

ImageName Class 0,0 0,1 0,2 0,3 0,4img_2_00_02 1 0 0 0 0 0img_2_00_03 1 0 38 22 0 0img_2_00_05 1 13 0 64 13 42...img_0_00_09 -1 34 53 0 38 0img_0_00_28 -1 0 64 0 98 93img_0_01_08 -1 13 0 0 59 13img_0_03_05 -1 34 34 0 0 0

画像の名称 クラス(1 or -1) 白黒の値.値が大きいと白っぽい

3

Page 4: Datamining r 4th

訓練データとテストデータ(2)• クラスは1か-1の2種類になっている• 訓練データはデータ数が1,000.内訳はClass=1が500枚,それ以外のClass = -1 が500枚• 2の画像を当てるusps_2_train.tab なら,2の画像データ(Class = 1)が500枚,それ以外(Class = -1)が500枚となっている• 同様に,5の画像を当てるusps_5_train.tabなら,5の画像(Class = 1)が500枚,それ以外(Class = -1)が500枚

• テストデータはデータ数が100.内訳は,Class=1が正解の画像が55枚,それ以外(Class=-1が正解)が45枚.• テストデータを利用するとき,各Classに何枚属しているかの情報は利用できないのが普通なので,予測には利用しない.

4

Page 5: Datamining r 4th

• 元の数字の画像は,http://lab.se-se.jp/~sesejun/lecture/usps/img_a_bb_cc.jpg で見ることができる• a は実際の数字.bb,ccは元の画像上の位置.bb,ccが異なれば,画像が異なる(無視して良い).

• たとえば,img_3_29_25は, http://lab.se-se.jp/~sesejun/ lecture/usps/img_3_29_25.jpg にある• 元の画像が16x16なので,小さいけど・・・

img_3_29_25 img_5_03_31 img_3_06_30 img_3_17_08

5

Page 6: Datamining r 4th

k-NN

Page 7: Datamining r 4th

Apply Family• 行列やリスト内の各行, 各列, 各要素に対する演算

• for文を廻しても計算できる• プログラムが見やすくなる&速度が速くなる

apply(X, 1, 関数) 各行に関数を適用

apply(X, 2, 関数) 各列に関数を適用

apply(X, c(1,2), 関数) 各要素に関数を適用

lapply(X, 関数)リストの各要素に関数を適用.結果はdataframeで返す.

sapply(X,関数)リストの各要素に関数を適用.

結果はtableで返す.

sweep(X, M, V) Xの各行(M=1),列(M=2),要素(M=c(1,2))からVを引く7

Page 8: Datamining r 4th

例1> m <- matrix((1:9)**2, nrow=3)> m [,1] [,2] [,3][1,] 1 16 49[2,] 4 25 64[3,] 9 36 81> apply(m, 1, sum)[1] 66 93 126> apply(m, 2, sum)[1] 14 77 194> apply(m, c(1,2), sqrt) [,1] [,2] [,3][1,] 1 4 7[2,] 2 5 8[3,] 3 6 9

> l <- list(a=1:3, b=4:6)> l$a[1] 1 2 3

$b[1] 4 5 6

> lapply(l, sum)$a[1] 6

$b[1] 15

> sapply(l, sum) a b 6 15

8

Page 9: Datamining r 4th

例2> m <- matrix((1:9)**2, nrow=3)> m [,1] [,2] [,3][1,] 1 16 49[2,] 4 25 64[3,] 9 36 81> apply(m, 1, sum)[1] 66 93 126> apply(m, 2, sum)[1] 14 77 194> apply(m, c(1,2), sqrt) [,1] [,2] [,3][1,] 1 4 7[2,] 2 5 8[3,] 3 6 9

> l <- list(a=1:3, b=4:6)> l$a[1] 1 2 3

$b[1] 4 5 6

> lapply(l, sum)$a[1] 6

$b[1] 15

> sapply(l, sum) a b 6 15

9

Page 10: Datamining r 4th

K-NNを実装してみる• ここでは既存のライブラリを使うのではなく,自分で実装する

> iris.train <- read.table("iris_train.csv", sep=",", header=T)> iris.test <- read.table("iris_test.csv", sep=",", header=T)

> q <- iris.test[1,1:4]

> diff <- sweep(iris.train[1:4], 2, t(q))

> diff * diff

> distquery <- apply(diff * diff, 1, sum)

> sort(distquery)

> order(distquery)

テストデータの属性ベクトル作成.ここではテストデータ(iris.test)の1行目のデータについて予測する

各訓練データと予測するテストデータとの距離を測る

全ての点に対し距離を計算して,近い順に並べる.並べ替え後の元のデータの位置を取得する.→どの点が最近点か分かる.

sweep(X, 2, V)は,Xをnxm行列とすると,Vは長さmのベクトルで,Xの各行からVの値を引く.applyはX =( ) , V = (2,1)とすると,結果は ( ) = ( )2 3

4 52-2 3-14-2 5-1

0 22 4 10

Page 11: Datamining r 4th

まず,1点の予測

> iris.train[order(distquery)[1:5],]

> iris.train[order(distquery)[1:5],]$Class

> knnclasses <- table(iris.train[order(distquery)[1:5],]$Class)

> as.factor(table(knnclasses)

> sortedtable <- sort(as.factor(table(knnclasses)), decreasing=T)

> labels(sortedtable)[1]

> predclass <- labels(sortedtable)[1]

> predclass == iris.test$Class[1]

最も近い5点のクラスを取得

各クラスの数を調べるおまじない(型の変換)

クラスを個数の順にソート一番個数の多い物を予測のクラスとする

予測と実際のクラスが合っているか確認

11

Page 12: Datamining r 4th

関数にする> knnpredict <- function(train,class,query,k) {+ diff <- sweep(train,2,query)+ distquery <- apply(diff * diff, 1, sum)+ knnclasses <- class[order(distquery)[1:k]]+ sortedtable <- sort(as.factor(table(knnclasses)), decreasing=T)+ labels(sortedtable)[1]+ }

> knnpredict(iris.train[1:4], iris.train$Class, t(iris.test[1,1:4]),5)

> knnpredict(iris.train[1:4], iris.train$Class, t(iris.test[10,1:4]),1)

> for (i in 1:length(rownames(iris.test))) {+ pred <- knnpredict(iris.train[1:4], iris.train$Class, t(iris.test[i,1:4]),10)+ result <- pred == iris.test[i,]$Class+ cat(paste(pred, iris.test[i,]$Class, result, sep="\t"))+ cat("\n")+ }

今までの作業をまとめて,一つの関数にする.

行頭の”+”は入力の必要有りません.

テストデータの1行目の点を5-NNで予測

テストデータの1行目の点を1-NNで予測全テストデータについて予測と本当の回答を出力

12

Page 13: Datamining r 4th

正答率を求める様に変更する

> resvec <- c()> for (i in 1:30) {+ pred <- knnpredict(iris.train[1:4], iris.train$Class, t(iris.test[i,1:4]),10)+ resvec <- append(resvec, pred == iris.test[i,]$Class)+ }> sum(resvec)/length(resvec)

結果を表示しただけでは,正答率を出すのに手間がかかるので,正答率が出るように変更.

13

Page 14: Datamining r 4th

レポート31. IRISデータについて

1. IRISデータの訓練データ中の4つの属性("Sepal.length","Sepal.width",

"Petal.length","Petal.width")に関し,それぞれの値の最大値,最小値,平均値を求めてください

2. IRISデータでは各属性毎に最大,最小,平均の値が異なります.この属性毎に値の大きさ(単位)が異なる環境下でK-NNを行った場合に起きうる問題点を理由と共に挙げ,解決方法を示して下さい.

2. USPSデータについて1. USPSのデータに対して,5-NNを行い,正答率を各文字(0-9)毎に計測してください.

2. K-NN の Kが変化すると正答率がどのように変化するか,考察してください3. USPSの各文字に関して,決定木及びナイーブベイズの予測を行い,K-NN,決定木,ナイーブベイズの間で正答率を比較してください.(K-NNのKは任意に決める事)

4. USPSの数字が与えられて,判別するには,どのようなプログラムを作成すれば良いか,提案すると共に議論して下さい.

14