スクリプト言語 ツインテールdeエンジェルモード!! で、簡単なXORニューラルネットのシミュレーションを実行してみたいと思います。
これは、オーム社「機械学習と深層学習(C言語によるシミュレーション)」(小高知宏著)にて説明されている、単純な階層型ニューラルネットプログラムを、スクリプト言語 ツインテールdeエンジェルモード!! でも、作成してみようというものです。
そして、「ソース規模」や「実行速度」の比較もしてみたいと思います。
(プログラム自体の説明については、本書をご覧ください。)
スクリプトの導入部分とメインプログラムはこんな感じになります。
(以下、インラインでコメント挿入)
>C言語のプリプロセッサ(マクロ)に相当する機能はないので、グローバル変数
>で似たようなことを実現してみました。
global INPUTNO = 2 /* 入力層のニューロン数 */
global HIDDENNO=2 /* 隠れ層のニューロン数 */
global DATANO =100 /* データセットの最大数 */
/* 重みと閾値の初期化&データの読み込み */
wh = initwh()
wo = initwo()
(n_of_e,e) = getdata(e)
print("Numbe of Data Set = %d\n",n_of_e)
/* メインループ */
for( i=0 ; i<n_of_e ; i++ ){ // 全ての入力データについて...
print("[%d] ",i)
for( j=0 ; j<INPUTNO ; j++ )
print("%f ",e[i][j])
o = forward(wh,wo,e[i])
print("%f\n",o)
}
重みと閾値の初期化をして、データを読み込んで、
順方向計算をする。という、とてもシンプルなものです。
前回やった、人工ニューロンのシミュレーションと大変似ています。
次に、初期化関数はこんな感じです。パラメーターは固定値となっています。
def initwh(){
wh[0][0] = -2
wh[0][1] = +3
wh[0][2] = -1
wh[1][0] = -2
wh[1][1] = +1
wh[1][2] = +0.5
retn(wh)
}
def initwo(){
wo = {-60,+94,-1}
retn(wo)
}
データの読み込み関数ですが、これは前回と全く同じなので省略します。
最後に、順方向計算関数です。
入力データを重みと掛け合わして、その結果を足し合せ、
最後に閾値を引いています。そして、それを2層に渡って計算しています。
なお、活性化関数は、ステップ関数となっています。
def forward(wh,wo,e){
/* z の計算 */
for( i=0 ; i<HIDDENNO ; i++ ){
u = 0.0
for( j=0 ; j<INPUTNO ; j++ )
u += wh[i][j]*e[j]
u -= wh[i][j] // 閾値
z[i] = (u>=0?1.0:0.0)
}
/* o の計算 */
o = 0.0
for( i=0 ; i<HIDDENNO ; i++ )
o += wo[i]*z[i]
o -= wo[i] // 閾値
retn( o>=0?1.0:0.0 )
}
では、実際に実行してみて、実行時間を測定してみます。
% time tt nn.tt < ch4/data24.txt
Numbe of Data Set = 4
[0] 0.000000 0.000000 0.000000
[1] 0.000000 1.000000 1.000000
[2] 1.000000 0.000000 1.000000
[3] 1.000000 1.000000 0.000000
real 0m0.010s
user 0m0.006s
sys 0m0.003s
単純な計算だけなので、あまり時間が掛かっていません。
なお、プログラムはXOR回路となりました。
次に、C言語によるバージョンで速度を測定してみます。
(といっても、ダウンロードバージョンではなく、
独自にC言語で作ったプログラムでの測定となります。)
% gcc -Wall nn.c
% time a.out < ch4/data24.txt
Numbe of Data Set = 4
[0] 0.000000 0.000000 0.000000
[1] 0.000000 1.000000 1.000000
[2] 1.000000 0.000000 1.000000
[3] 1.000000 1.000000 0.000000
real 0m0.001s
user 0m0.000s
sys 0m0.000s
流石C言語という感じですね!
丁度10倍の速度で処理が終わっています。
最後に、ソース規模(ソース行数)の比較です。
書籍では、154行(C言語)ですが、
スクリプト言語 ツインテールdeエンジェルモード!! では、
% wc -l nn.tt
70 nn.tt
70行で済みました。あと、数字では表しにくいのですが、プログラムの記述の
しやすさも、スクリプト言語の方が、かなりお気楽でした。
この辺り(お気楽さ)は、軽量言語の得意分野ですね!!
用途に合わせた、適材適所な選択がベストな選択だと思います。