はじめに
PAアルゴリズムは回帰問題にも適用することができる、と書いてあったのでとりあえず試してみた。
パラメータの設定などがわかっていないので、要調査。
結果
- 学習データでクローズテスト
- パラメータは適当に設定
- C = 0.005
- ε = 1.0
- 学習回数は、データ全部を10ループ
- グラフについて
- 縦軸 : データの一番左の実数値
- 横軸 : 事例番号(データの上から0,1,2,3,...)
- 意外と学習データの近いところにはいる
- 最大値付近や最小値付近でずれが大きいように見える
- 学習の順番がランダムなほど学習データに近い値がでているように見える
- やっぱり学習する順番はランダムな方がいいかもしれない
- パラメータの設定の仕方がよくわからない
用いたコード
#! /usr/bin/perl
use strict;
use warnings;
my $train_file = shift;
my $C = shift;
my $epsilon = shift;
my $loop = 10;
my $w = {};
my @x_list;
my @t_list;
open IN, $train_file;
while(<IN>){
chomp;
my @list = split(/\s+/, $_);
push(@t_list, $list[0]);
my $hash;
for(my $i=1; $i<@list; $i++){
my ($a, $b) = split(/:/,$list[$i]);
$hash->{$a} = $b;
$w->{$a} = 0;
}
push(@x_list, $hash);
}
while($loop--){
for(my $i = 0; $i < @x_list; $i++){
train($w, $x_list[$i], $t_list[$i]);
}
}
my $num = 0;
while(<>){
chomp;
my @list = split(/\s+/, $_);
my $hash;
for(my $i=1; $i<@list; $i++){
my ($a, $b) = split(/:/,$list[$i]);
$hash->{$a} = $b;
}
my $t = predict($w, $hash);
print $num,"\t",$t,"\t",$list[0],"\t",($t-$list[0]),"\n";
$num++;
}
sub predict {
my ($w, $x) = @_;
my $y = 0;
foreach my $f (keys %$x){
if($w->{$f}){
$y += ($w->{$f} * $x->{$f});
}
}
return $y;
}
sub loss {
my ($w, $x, $t) = @_;
my $y = 0;
foreach my $f (keys %$x){
if($w->{$f}){
$y += ($w->{$f} * $x->{$f});
}
}
return 0.0 if(abs($y-$t) <= $epsilon);
return abs($y-$t)-$epsilon;
}
sub train {
my ($w, $x, $t) = @_;
my $y = predict($w, $x);
my $l = loss($w, $x, $t);
my $sq_x = 0.0;
foreach my $f (keys %$x){
$sq_x += ($x->{$f} * $x->{$f});
}
my $tau = $l / ($sq_x + 1.0 / (2 * $C));
my $sign = 1;
$sign = -1 if($t-$y < 0);
foreach my $f(keys %$x){
$w->{$f} += $sign * $tau * $x->{$f};
}
}