[連載]フリーソフトによるデータ解析・マイニング第31回

Rとカーネル法・サポートベクターマシン

1.カーネル法とは

 図1に示すように、非線形データ構造を線形構造に変換することができれば、線形データ解析手法で非線形データを容易に扱うことができる。

変換による線形化のイメージ

図1 変換による線形化のイメージ

 データを変換することで、非線形構造を線形構造に変換することが可能である。例えば、図2(a)に示す2次元平面座標系(x,y)上の4つの点A1(1,1)、A2(1,-1)、A3(-1,-1)、A4(-1,1)を考えよう。仮にA1とA3がひとつのクラス、A2とA4がひとつのクラスだとすると、平面上でクラスの境界線を一本の直線で引くことができない。しかし、新しい変数 を導入し、2次元平面(x,y)上の4つの点を3次元空間(x,y,z)に射影するとA1(1,1,1)、A2(1,-1,-1)、A3(-1,-1,1)、A4(-1,1,-1)になり、両クラスは平面で切り分けることが可能である。例えば,z=0の平面を境界面とすることができる。

図2 データ写像の例

図2 データ写像の例


 図1では、関数φ(x)を用いて個体の特徴・属性ベクトルについて変換を施している。関数φ(x)は、通常高次元への写像関数で、xを入力空間、変換されたFを特徴空間と呼ぶ。
 従来のデータ解析方法では、高い次元のデータを低次元に縮約して分析を行う。その典型的な方法としては、主成分分析、因子分析、対応分析、多次元尺度法などがある。
 データを高い次元の特徴空間に射影すると非線形問題を線形問題に置き換えることが可能であるが、計算量が増える。カーネル(kernel)法は、データを高次元に射影し、線形問題に置き換えると同時に計算量の問題を解決する技法である。
 カーネル法では射影された高次元のデータを直接計算するのではなく、任意の個体x,zを変換したφ(x)、φ(z)の内〈φ(x),φ(z)〉のような処理を借りて間接的に高次元のデータについて計算処理を行う。このようなデータの変換と内積のような演算を組み合わせた関数をカーネル関数と呼び、K(x,z)=〈φ(x),φ(z)〉のように表記する。カーネルに関する厳密な定義やカーネル関数の性質などについては[1]、 [3]、[4]が詳しい。
 カーネル法を取り入れた幾つかのデータ解析方法が提案されている。例えば、カーネル主成分分析、カーネル正準相関分析、カーネルクラスター分析、カーネルk平均ほう、カーネル回帰分析、カーネル判別分析などがある。本稿では、カーネル主成分分析とカーネル法による分類器サポートベクターマシンについて紹介する。

2.カーネル主成分分析

 カーネル主成分分析(KPCA; kernel principal component analysis)は、非線形主成分分析とも呼ばれている。カーネル主成分分析には幾つかのアルゴリズムが提案されているが、その大まかな流れは次のステップを取る。

 (1) カーネル関数K(x,z)=〈φ(x),φ(z)〉を決める
 (2) データから写像行列Km×nを求める
 (3) Km×nの固有値と固有ベクトル
 (4) 固有値と固有ベクトルを正規化する

2.1 パッケージと関数

 パッケージkernlabには,カーネル主成分分析の関数kpcaがある。パッケージkernlabはCRANミラーサイトからダウンロードできる。次に関数kpcaの書き式を示す。

kpca(x, kernel = "rbfdot", features=0, kpar= list(sigma = 0.1),...)

 引数xはマトリックスとデータフレーム形式のデータである。引数kernelでは、用いるカーネル関数を指定する。デフォルトには"rbfdot"(ガウシアン)が指定されているが、これ以外に、カーネル関数"polydot"(多項式)、"vanilladot"(線形),"tanhdot"(タンジェント)、"laplacedot"(ラプラシアン)、"besseldot"(ベッセル)、"anovadot"(ANOVA RBF)、"splinedot"(スプライン)が用意されている。これらの関数は [2]に定義されている。
 引数featuresでは、求める主成分の数を指定する。デフォルトはゼロになっている。引数kparはカーネル関数に用いるパラメータを指定する。
 結果としては、固有値eig(),主成分ベクトルkpc()、用いたデータの主成分得点pcv()、回転・射影後の主成分得点rotated()が返される。

2.2 カーネル主成分分析の例

 次にデータirisを用いた主成分得点の散布図を作成するコマンドとその結果を図3(a)に示す。

> library(kernlab)
> x<-as.matrix(iris[,1:4])
> iris.kpc1<-kpca(x,kernel="rbfdot", features=2,kpar=list(sigma=0.1))
> plot(pcv(iris.kpc1), col=as.integer(iris[,5]))

 カーネル主成分析法は、古典的主成分分析方法と異なり、用いるカーネル関数およびkparのパラメータによって返される結果が異なる。カーネル関数をkernel="polydot"、kparのパラメータをlist(degree =1))にしたコマンドラインとその結果を図3(b)に示す。

図3 irisのカーネル主成分得点散布図(a)

図3 irisのカーネル主成分得点散布図(a)

図3 irisのカーネル主成分得点散布図(b)

図3 irisのカーネル主成分得点散布図(b)

 このようにカーネル関数、kparのパラメータは主成分の結果に大きく影響する。どのようなカーネル関数を用い、kparのパラメータをどのような値にするべきであるかに関しては、用いるデータに依存するので、経験に頼るのが現状である。
 次にiris.kpcの結果を用いて新しいデータnew.dataを当てはめる書き式を示す。

predict(kpc(iris.kpc),new.data)

3.サポートベクターマシン

 サポートベクターマシン(SVM; support vector machine)は、分類と回帰問題を主としたデータ解析方法で、広く知られるようになったのは1990年代の中頃であり、Vapnik,Vの貢献が高く評価されている。support vector machineをサポートベクターマシンと訳するかそれともサポートベクトルマシンと訳するかについては議論があるが、本稿ではサポートベクターマシンと呼ぶことにする。SVMは高次元の分類問題が得意であると言われている。
 SVMは、カーネル関数の力を借りて、線形分離可能な高次元の空間で線形的なアプローチで学習を行うアルゴリズムである。
 学習データ集合(x1,y1 )、(x2,2)、・・・(xm,ym)があるとする。このx=(x1,x2, ・・・xn)は個体の特徴ベクトル、yは目的変数である。yは回帰問題では数値、分類問題ではクラスのラベルである。
 通常の線形回帰と線形判別の問題では次に示す線形モデルを用いる.図4における点線上の個体をサポートベクターと呼ぶ。



図4 SVMのイメージ

図4 SVMのイメージ

 初期のSVMは2群線形分類器として提案されたが,多くの改良が施されている.その1つが,カーネル法を用いたSVMである。カーネル法によるSVMはカーネル関数を用いて次に示す線形関数で表されるが,非線形分類器である。

 式の最適化は特徴空間でクラス間のマージンを最大にするアプローチで行う.  ここの係数ベタは学習データにおける目的変数yの関数である。詳細に関しては[3][4][5]などが詳しい。  

3.1 パッケージと関数

 ここではパッケージkernlabの中のSVM関数ksvmを紹介する。関数ksvmの書き式を次に示す。

ksvm(formula, data, kernel ="rbfdot", kpar=list(sigma = 0.1), type=NULL, cross = 0,・・・)

 引数formulaはモデルに用いるデータの書き式、dataは用いるデータ、引数kernelとkparは前節で説明したカーネル関数と関数に用いるパラメータである。
 引数typeでは、分類と回帰のタイプを指定する。デフォルトは、目的変数が質的データの場合はC-svc分類法、量的データの場合はeps-svr回帰を行うように設定されている。分類方法としては"nu-svc"、"C-bsvc"、回帰方法としては"nu-svr"、"eps-svr"が用意されている。引数cross ではn重交差確認法のnを指定する。デフォルトはゼロになっている。
 テストデータを訓練結果へ当てはめる関数はpredictである。

3.2 データと関数の使用例

 パッケージkernlabには、分類問題として面白いデータセットspamが用意されている。データセットは、4601の電子メールを58項目に分けて記録したものである。第58列がクラス情報spam,nonspamで、残りの57項目はメールの特徴を記録したものである。このspamとは受け取りたくないのに届いた迷惑メールを指す。

> library(kernlab)
> data(spam);dim(spam)
[1] 4601  58
> table(spam[,58])
nonspam  spam
  2788   1813

 返された結果から分かるようにデータは1813のspamメールと2788のnonspamメールにより構成されている。データセットの第1列から48列までは、データspamの変数の名前に用いた文字列がメールに使用された頻度である.ただし、num857のようにnum***になっているのは,その数値***が現れた頻度である。49列から54列までは記号;、(、[、!、$、#の使用頻度、55列から57列は、メールに用いられた大文字の平均値、大文字が連続使用された最も長い文字列の文字数、用いられた大文字の総数である。
 まずデータセットspamから、訓練用データとテスト用データを作成する。ここではサンプリング方法を用いることにする。同じサンプリング結果を再現するため、乱数のシード(種)を関数set.ssedで指定する。用いるシードの番号は自由であるが、ここでは番号50を用いる。このシードを用いることにより、読者のマシン上でも同じ乱数が得られる。ここでは訓練用データの個体数を2500にし、その残りをテスト用とする。

> set.seed(50)
> tr.num<-sample(4601,2500)
> spam.train<-spam[tr.num,]
> spam.test<-spam[-tr.num,]

 訓練データを用いて学習を行い、その結果に基づいて関数predictを用いてテストを行うことにする。

> spam.svm <- ksvm(type~.,data=spam.train, kernel="rbfdot",kpar=list(sigma=0.01))
> spam.pre <- predict(spam.svm, spam.test[,-58])
> (spam.tab<-table(spam.test[,58], spam.pre))

spam.pre
  nonspam spam
nonspam 1226 56
spam 96 723
> 1-sum(diag(spam.tab))/sum(spam.tab)
[1] 0.0723465

 ランダムサンプリングした2500のメールを用いて学習を行い、残り2101のメールについてテストを行った結果、誤判別(識別)率は約0.0724である。
 学習データを用いて交差確認法で、誤判別率などについて考察を行うこともできる。交差確認法のnを10にしたコマンドラインとその結果を次に示す。

> (train.cro <- ksvm(type~.,data=spam.train,kernel="rbfdot",kpar=list(sigma=0.05), C=5,cross=10)) (train.cro <- ksvm(type~.,data=spam.train,kernel=

 結果として、学習のエラーと交差確認のエラーが返される。返された交差確認のエラーは0.082である。この値は、テストデータを用いて行ったテストの結果0.072と大きい差がない。このように、交差確認法を用いて、作成したモデルの精度を把握することができる。
 用いるデータが2変数で、2クラスに分類する問題の場合は、関数plotを用いてカラフルな散布図を作成することができる。
 データirisの一部分を用いた例のコマンド次に,返される散布図を図5に示す。

> set.seed(10)
> y<-as.matrix(iris[51:150,5])
> iris1<-data.frame(iris[51:150,3:4],y)
> ir.ksvm<- ksvm(y~.,data=iris1)
> plot(ir.ksvm,data=iris1[,1:2])
> table(iris1$y,predict(ir.ksvm,iris1[,1:2]))

  versicolor virginica
versicolor 48 2
virginica 3 47

図5 irisのSVM分類図

図5 irisのSVM分類図

3.3 回帰分析のケーススタディ

 関数ksvmによる回帰分析の書き式は,判別の問題と基本的には同じである。関数ksvm のパフォマンスを示すため,多項式回帰を説明する際に作成した多項式曲線の人工データを用いることにする。

> x1=seq(-10,10,0.1);set.seed(10)
> y1=50*sin(x1)+x1^2+10*rnorm(length(x1),0,1)

 説明変数をx1,目的変数をy1にした関数ksvmの使用例のコマンドを次に示す。

> xy.svm<-ksvm(x1,y1,epsilon=0.01,kpar=list(sigma=16))
> sy.pre<-predict(xy.svm,x1)
> plot(x1,y1,type="l")
> lines(x1,sy.pre,col="red",lty=2)
> legend(locator(1),c("実測値","予測値"), lty=c(1,2),col=c(1,2))


図6回帰問題における実測値と関数ksvmの予測値

図6 回帰問題における実測値と関数ksvmの予測値

4 その他

 パッケージkernlabには、データの特徴を分析するアルゴリズム関数kfa(Kernel Feature Analysis)、カーネルヘッビアン(Kernel Hebbian)アルゴリズムによる主成分分析関数khc、カーネル準相関分析関数kcca、適合ベクターマシン関数rvm(Relevance Vector Machine)などがある。現段階の関数rvmは回帰分析のみが機能している。
 カーネル法は機械学習、パターン分析の方法として、研究・応用が広がりつつある。カーネル法によるパターン分析に関しては[1]が詳しい。
 SVMは、狭義の分類と回帰問題だけではなく、自然言語処理などへも応用されている。カーネル法とSVMの基礎理論に関しては [3]、[4]が詳しい。またSVMに関しては [5]がある。
 群平均法(group average method)は、最近隣法と最遠隣法を折衷した方法で、2つのクラスターのそれぞれの中から1個ずつ個体を選んで個体間の距離を求め、それらの距離の平均値を2つのクラスター間の距離とする。
 SVMは、パッケージklaR、e1071にも実装されている。
 カーネル法は回帰、平滑化や密度の推定などにも多く用いる。パッケージstatsには平滑化に関する関数kernel 、kernapply 、ksmooth、密度を推定する関数densityがある。
 カーネル法による関数ksmoothを用いたカーネル回帰平滑化の例のコマンドとその結果を次に示す。

>attach(cars)
>plot(speed, dist)
>lines(ksmooth(speed, dist, "normal", bandwidth=1.3), col=2)
>lines(ksmooth(speed, dist, "normal", bandwidth=4), col=3,lty=2)
>detach("cars")


図7 関数ksmoothによるカーネル回帰平滑化

図7 関数ksmoothによるカーネル回帰平滑化

 カーネル法による平滑化関数パッケージとしてはKernSmooth、ksがあり、パッケージade4 、assist 、fields 、lattice、splancs、sandwichなどにもカーネル法に関連する関数がある。

参考文献
[1] J.Shawe-Taylor and N. Cristianini (2004): Kernel Methods for Pattern Analysis, Cambridge.
[2] Karatzoglou, A., Smola, A., hornik, K., Zeileis,A.(2004): kernlab-An S4 Package for Kernel Methods in R, Journal of statistical Software, Vol.11, Is.9, p.1-20. http://www.jstasoft.org
[3] 麻生英樹, 津田宏治, 村田昇(2003): パターン認識と学習の統計学―新しい概念と手法,岩波書店
[4] 大北剛訳(2005): サポートベクターマシン入門,共立出版
[5] 前田英作(2001): 痛快!サポートベクトルマシン - 古くて新しいパターン認識手法 - ,情報処理学会誌, Vol.42, No.7, p.676-683