Perceptron
をテンプレートにして作成
home
>
サイトマップ
開始行:
RIGHT:寄稿:東條遼平
* 基本の学習モデル [#g962739f]
最近傍決定則やk-最近傍決定則
によりパターンを識別する事ができるようになりました。
これらの方法は大変シンプルな考え方でありながら、サンプル...
かなりの精度で識別が可能だと考えられます。しかし問題点と...
サンプル全てを保持しておかなければならない事、次元数が増...
計算量が膨大になる事が挙げられます。
ここで最近傍決定則のように、パターンに最も距離の近いクラ...
見方を変えると、異なるクラスタのサンプル間において、
垂直二等分線を考え、領域を分けるという事になります。
#ref(perceptron1.png,nolink)
ということは、この境界線を知ることができれば、
サンプルのデータは不要と考えることができ、Perceptronはこ...
学習によって得ることができます。ただし、Perceptronは上の...
学習であたえられたデータ全てが分割できるような線を適当に...
#ref(perceptron2.png,nolink)
理想的にはCluster1とCluster2は境界Aで分割されて欲しくても、
図のようなサンプルで学習を行った場合境界Bで分割されること...
そのため図のように未知データが入って来たとき、理想的にはC...
Cluster2と判断されるかもしれないということです。したがっ...
十分に行う必要があります。
* ニューロンのモデル [#h98a3055]
さて、上の図における境界線を学習するために生理学における...
ネットワークモデルを考えます。
#ref(perceptron3.png,nolink)
丸をニューロン、線をシナプスだと考えます。
他のニューロンより信号xが伝わり、wの重み付けがされてニュ...
実際には電位として信号が伝わっているようですが、この電位...
ある閾値を越えるとそのニューロンは活性化(発火)します。
このモデルより、人工的に次のようなネットワークを作成しま...
#ref(perceptron4.png,nolink)
左より「入力層」、「中間層」、「出力層」といいます。
この出力層のユニット(ニューロン)が1つの場合、これを単純パ...
入力層と中間層、中間層と出力層の間の矢印一つ一つにそれぞ...
重みが存在します。パーセプトロンは学習によってこの重みを...
しかし、学習するのは中間層と出力層の間の重みだけで、
入力層と中間層の間の重みは固定であるため、実質3層ではな...
考えられます。
* 単純パーセプトロン [#mf4a00b3]
実質2層ということで「入力層」と「出力層」、その間を繋ぐ...
入力層のユニット数は扱いたいパターンの次元に相当します。
#ref(perceptron5.png,nolink)
入力層において入力信号は素通りしますので、出力層において、
#ref(img197.png,nolink)
という値が入って来ます。ここでニューロンはある閾値を越え...
#ref(img198.png,nolink)
となり、この値がゼロ以上であれば発火ということで1を出力し、
ゼロより小さければ発火しなかったということでゼロを出力し...
よって入力と出力の関係は次のようになります。
#ref(img199.png,nolink)
ここでf(.)とはゼロ以上の値が入って来たときに1、それ以外で...
また、閾値を意識せずに処理することができるように、入力層...
仮想的にもう一つ常に1を出力するユニットを考えN+1次元にし...
ユニットとの荷重を閾値(-θ)と考えると、
#ref(img200.png,nolink)
となり、シンプルに記述できます。これは入力ベクトルと重み...
f(.)に渡しているとも考えられます。
* 学習方法 [#i2255f3c]
それではANDを例に学習の手順を書いてみます。ANDとはプログ...
ANDやORのANDです。ANDの入出力は次のようになります。
入力が0(偽)と0(偽)ならば出力は0(偽)
入力が0(偽)と1(真)ならば出力は0(偽)
入力が1(真)と0(偽)ならば出力は0(偽)
入力が1(真)と1(真)ならば出力は1(真)
これは図で表すと次のように分離することになります。
#ref(perceptron6.png,nolink)
2次元で考えているので線で分離されていますが、一般的には超...
事になります。
ここで、実際には閾値があるので多少座標は違っているのです...
#ref(img200.png,nolink)
の式における重みwのベクトルが超平面の法線ベクトルとなり、
(1,1)座標の領域の方を向いていることになります。
ここで学習は次の式で行います。
#ref(img201.png,nolink)
ηは学習率といい1以下の正の定数です。tは教師データでoは入...
出力です。つまり、出力が正しければ(教師データと同じであれ...
1を出力すべきところ(t=1)を0と出力すれば(o=0)結合荷重はηx...
0を出力すべきところ(t=0)を1と出力すれば(o=1)結合荷重はηx...
ここで、なんでベクトルの足し算と引き算で学習ができるのか...
閾値の関係で多少違いますが、
例えば、間違って1が出力されたとき、次のようになっています。
#ref(perceptron7.png,nolink)
このときベクトルの引き算が行われるため、
#ref(perceptron8.png,nolink)
のように超平面が変化します。逆に間違って0が出力されたとき...
#ref(perceptron9.png,nolink)
となっているのが、
#ref(perceptron10.png,nolink)
のように変化します。
* Perceptronで扱える問題 [#jcb6b131]
今回出力層のユニットが1つの単純パーセプトロンを考えました...
「出力が1のときクラスタ1に属する」、「出力が0のときクラス...
考えると、単純パーセプトロンを組合せ、例えば数字の画像を...
#ref(perceptron11.png,nolink)
として、出力層の上から「数字が1のとき1、それ以外で0」、「...
一つ目の出力のみが1となったときに数字の1が書かれていたと...
ただし、超平面で領域を分割しなければいけないため、線型分...
例えばXORのような問題はパーセプトロンでは解くことができま...
* ソースコード [#fb2fe285]
説明が長くなってしまいましたが、ソースコードは簡単です。
double StepFunction(double net)
{
return net < 0 ? 0 : 1;
}
これは説明中にf(.)として出てきた関数です。
void Forward(double *input, double *output,
int ni, int no, double wio[ni][no])
{
int i, j;
double net;
input[ni-1] = 1;
for(i=0; i<no; i++){
net = .0;
for(j=0; j<ni; j++){
net += wio[j][i]*input[j];
}
output[i] = StepFunction(net);
}
}
inputが入力層のベクトル、outputが出力層のベクトルです。
ni,noはそれぞれ入力層、出力層のユニットの数で、wioは入力...
結合荷重となります。input[ni-1]=1はinputの最後の要素を仮...
常に1を出力するようにしているからです。この関数によって入...
ネットワークの出力を得ることができます。
void Backward(double *input, double *output, int ni, int...
double wio[ni][no], double eta, double *...
{
int i, j;
for(i=0; i<no; i++){
for(j=0; j<ni; j++){
wio[j][i] += eta*(teacher[i] - output[i])*input[j];
}
}
}
Forwardの後に呼ぶことで学習が行えます。
teacherとは教師データです。以上でパーセプトロンの関数は完...
mainの方も多少解説しておきます。
double teacher[4][3] = {
{0, 0, 0},
{1, 0, 0},
{0, 1, 0},
{1, 1, 1}
};
これが教師データです。左から2つが入力、右の部分が対応する...
今回ANDを学習させています。
for(i=0; i<INPUTSIZE; i++){
for(j=0; j<OUTPUTSIZE; j++){
weight_io[i][j] = ((double)rand()/RAND_MAX)/10;
}
}
INPUTSIZE,OUTPUTSIZEはそれぞれ入力層と出力層のユニット数、
weight_ioは結合荷重で、0から0.1までの乱数で初期化していま...
ここで入力層のユニットは仮想ユニットの分が含まれ3つになっ...
for(i=0; i<LOOPNUM; i++){
for(j=0; j<4; j++){
input[0] = teacher[j][0];
input[1] = teacher[j][1];
Forward(input, output, INPUTSIZE, OUTPUTSIZE, weight...
Backward(input, output, INPUTSIZE, OUTPUTSIZE,
weight_io, 0.01, &teacher[j][2]);
}
}
LOOPNUM回通り学習させています。線型分離可能な問題であれば、
これが終わればネットワークがしっかりと構築されているはず...
Forwardを使えば入力に対する理想的な出力が得られるハズです。
- &ref(main.c);
- &ref(neuralnet.c);
- &ref(neuralnet.h);
終了行:
RIGHT:寄稿:東條遼平
* 基本の学習モデル [#g962739f]
最近傍決定則やk-最近傍決定則
によりパターンを識別する事ができるようになりました。
これらの方法は大変シンプルな考え方でありながら、サンプル...
かなりの精度で識別が可能だと考えられます。しかし問題点と...
サンプル全てを保持しておかなければならない事、次元数が増...
計算量が膨大になる事が挙げられます。
ここで最近傍決定則のように、パターンに最も距離の近いクラ...
見方を変えると、異なるクラスタのサンプル間において、
垂直二等分線を考え、領域を分けるという事になります。
#ref(perceptron1.png,nolink)
ということは、この境界線を知ることができれば、
サンプルのデータは不要と考えることができ、Perceptronはこ...
学習によって得ることができます。ただし、Perceptronは上の...
学習であたえられたデータ全てが分割できるような線を適当に...
#ref(perceptron2.png,nolink)
理想的にはCluster1とCluster2は境界Aで分割されて欲しくても、
図のようなサンプルで学習を行った場合境界Bで分割されること...
そのため図のように未知データが入って来たとき、理想的にはC...
Cluster2と判断されるかもしれないということです。したがっ...
十分に行う必要があります。
* ニューロンのモデル [#h98a3055]
さて、上の図における境界線を学習するために生理学における...
ネットワークモデルを考えます。
#ref(perceptron3.png,nolink)
丸をニューロン、線をシナプスだと考えます。
他のニューロンより信号xが伝わり、wの重み付けがされてニュ...
実際には電位として信号が伝わっているようですが、この電位...
ある閾値を越えるとそのニューロンは活性化(発火)します。
このモデルより、人工的に次のようなネットワークを作成しま...
#ref(perceptron4.png,nolink)
左より「入力層」、「中間層」、「出力層」といいます。
この出力層のユニット(ニューロン)が1つの場合、これを単純パ...
入力層と中間層、中間層と出力層の間の矢印一つ一つにそれぞ...
重みが存在します。パーセプトロンは学習によってこの重みを...
しかし、学習するのは中間層と出力層の間の重みだけで、
入力層と中間層の間の重みは固定であるため、実質3層ではな...
考えられます。
* 単純パーセプトロン [#mf4a00b3]
実質2層ということで「入力層」と「出力層」、その間を繋ぐ...
入力層のユニット数は扱いたいパターンの次元に相当します。
#ref(perceptron5.png,nolink)
入力層において入力信号は素通りしますので、出力層において、
#ref(img197.png,nolink)
という値が入って来ます。ここでニューロンはある閾値を越え...
#ref(img198.png,nolink)
となり、この値がゼロ以上であれば発火ということで1を出力し、
ゼロより小さければ発火しなかったということでゼロを出力し...
よって入力と出力の関係は次のようになります。
#ref(img199.png,nolink)
ここでf(.)とはゼロ以上の値が入って来たときに1、それ以外で...
また、閾値を意識せずに処理することができるように、入力層...
仮想的にもう一つ常に1を出力するユニットを考えN+1次元にし...
ユニットとの荷重を閾値(-θ)と考えると、
#ref(img200.png,nolink)
となり、シンプルに記述できます。これは入力ベクトルと重み...
f(.)に渡しているとも考えられます。
* 学習方法 [#i2255f3c]
それではANDを例に学習の手順を書いてみます。ANDとはプログ...
ANDやORのANDです。ANDの入出力は次のようになります。
入力が0(偽)と0(偽)ならば出力は0(偽)
入力が0(偽)と1(真)ならば出力は0(偽)
入力が1(真)と0(偽)ならば出力は0(偽)
入力が1(真)と1(真)ならば出力は1(真)
これは図で表すと次のように分離することになります。
#ref(perceptron6.png,nolink)
2次元で考えているので線で分離されていますが、一般的には超...
事になります。
ここで、実際には閾値があるので多少座標は違っているのです...
#ref(img200.png,nolink)
の式における重みwのベクトルが超平面の法線ベクトルとなり、
(1,1)座標の領域の方を向いていることになります。
ここで学習は次の式で行います。
#ref(img201.png,nolink)
ηは学習率といい1以下の正の定数です。tは教師データでoは入...
出力です。つまり、出力が正しければ(教師データと同じであれ...
1を出力すべきところ(t=1)を0と出力すれば(o=0)結合荷重はηx...
0を出力すべきところ(t=0)を1と出力すれば(o=1)結合荷重はηx...
ここで、なんでベクトルの足し算と引き算で学習ができるのか...
閾値の関係で多少違いますが、
例えば、間違って1が出力されたとき、次のようになっています。
#ref(perceptron7.png,nolink)
このときベクトルの引き算が行われるため、
#ref(perceptron8.png,nolink)
のように超平面が変化します。逆に間違って0が出力されたとき...
#ref(perceptron9.png,nolink)
となっているのが、
#ref(perceptron10.png,nolink)
のように変化します。
* Perceptronで扱える問題 [#jcb6b131]
今回出力層のユニットが1つの単純パーセプトロンを考えました...
「出力が1のときクラスタ1に属する」、「出力が0のときクラス...
考えると、単純パーセプトロンを組合せ、例えば数字の画像を...
#ref(perceptron11.png,nolink)
として、出力層の上から「数字が1のとき1、それ以外で0」、「...
一つ目の出力のみが1となったときに数字の1が書かれていたと...
ただし、超平面で領域を分割しなければいけないため、線型分...
例えばXORのような問題はパーセプトロンでは解くことができま...
* ソースコード [#fb2fe285]
説明が長くなってしまいましたが、ソースコードは簡単です。
double StepFunction(double net)
{
return net < 0 ? 0 : 1;
}
これは説明中にf(.)として出てきた関数です。
void Forward(double *input, double *output,
int ni, int no, double wio[ni][no])
{
int i, j;
double net;
input[ni-1] = 1;
for(i=0; i<no; i++){
net = .0;
for(j=0; j<ni; j++){
net += wio[j][i]*input[j];
}
output[i] = StepFunction(net);
}
}
inputが入力層のベクトル、outputが出力層のベクトルです。
ni,noはそれぞれ入力層、出力層のユニットの数で、wioは入力...
結合荷重となります。input[ni-1]=1はinputの最後の要素を仮...
常に1を出力するようにしているからです。この関数によって入...
ネットワークの出力を得ることができます。
void Backward(double *input, double *output, int ni, int...
double wio[ni][no], double eta, double *...
{
int i, j;
for(i=0; i<no; i++){
for(j=0; j<ni; j++){
wio[j][i] += eta*(teacher[i] - output[i])*input[j];
}
}
}
Forwardの後に呼ぶことで学習が行えます。
teacherとは教師データです。以上でパーセプトロンの関数は完...
mainの方も多少解説しておきます。
double teacher[4][3] = {
{0, 0, 0},
{1, 0, 0},
{0, 1, 0},
{1, 1, 1}
};
これが教師データです。左から2つが入力、右の部分が対応する...
今回ANDを学習させています。
for(i=0; i<INPUTSIZE; i++){
for(j=0; j<OUTPUTSIZE; j++){
weight_io[i][j] = ((double)rand()/RAND_MAX)/10;
}
}
INPUTSIZE,OUTPUTSIZEはそれぞれ入力層と出力層のユニット数、
weight_ioは結合荷重で、0から0.1までの乱数で初期化していま...
ここで入力層のユニットは仮想ユニットの分が含まれ3つになっ...
for(i=0; i<LOOPNUM; i++){
for(j=0; j<4; j++){
input[0] = teacher[j][0];
input[1] = teacher[j][1];
Forward(input, output, INPUTSIZE, OUTPUTSIZE, weight...
Backward(input, output, INPUTSIZE, OUTPUTSIZE,
weight_io, 0.01, &teacher[j][2]);
}
}
LOOPNUM回通り学習させています。線型分離可能な問題であれば、
これが終わればネットワークがしっかりと構築されているはず...
Forwardを使えば入力に対する理想的な出力が得られるハズです。
- &ref(main.c);
- &ref(neuralnet.c);
- &ref(neuralnet.h);
ページ名:
home
>
Modified by
物理のかぎプロジェクト
PukiWiki 1.4.5_1
Copyright © 2001-2005
PukiWiki Developers Team
. License is
GPL
.
Based on "PukiWiki" 1.3 by
yu-ji
Powered by PHP 5.3.29HTML convert time to 0.004 sec.